问题描述
我的 check() 函数(代码顶部)中的 strcasecmp 无法正常工作。当我运行代码时,它不会不区分大小写。我认为这与我比较的类型有关,但我还想不通...... PS:它来自 CS50 但我已经提交了问题,所以这里没有作弊 ;)
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <strings.h>
#include <string.h>
#include <ctype.h>
#include "dictionary.h"
// Represents a node in a hash table
typedef struct node
{
char word[LENGTH + 1];
struct node *next;
}
node;
// Number of buckets in hash table
const unsigned int N = 1000; //CHANGE THIS ACCORDING TO HASH ALGORITHM
// Hash table
node *table[N];
// used for size() to keep track of dictionary size
int dict_size = 0;
// Returns true if word is in dictionary (case-insensitive),else false
bool check(const char *word)
{
//1: hash word to obtain hash value
//2: access linked list at that index in hash table
//cursor = first item of linked list
node *cursor = table[hash(word)];
//then move the cursor until it's NULL
//use cursor (cursor = cursor->next) to traverse through linked list
//true if word found
while(cursor != NULL)
{
//has to be ZERO! strcasecmp returns numbers if the words differ,not true or false
if (strcasecmp(cursor->word,word) == 0)
{
return true;
}
cursor = cursor->next;
}
//false if reached NULL and word has not been found
return false;
}
//Hashes word to a number
//takes word as input
//outputs a number corresponding to which "bucket" (index in an array) to store the word
//Could do first letter,first two letters,MATH??? ---> SEARCH ONLINE AND GIVE THE SOURCE
unsigned int hash(const char *word)
{
//make it deterministic
//use SDBM Hash Function from source
unsigned hashval;
for (hashval = 0; *word != '\0'; word++)
{
hashval = *word + 31 * hashval;
}
return hashval % N;
//SOURCE: https://stackoverflow.com/questions/7666509/hash-function-for-string
}
// Loads dictionary into memory,returning true if successful,else false
bool load(const char *dictionary)
{
//1: open dict file
FILE *dict = fopen(dictionary,"r");
char expression[LENGTH + 1];
//check for return value NULL
if (dict == NULL)
{
printf("Could not open file!");
return false;
}
//FOR EVERY WORD IN DICT!
//2: read strings ("expression") from file one at a time
//do until fscanf returns EOF
while (fscanf(dict,"%s",expression) != EOF)
{
//count words (in global variable) to determine size of dict
dict_size++;
//3: create a new node for each word
//use malloc to make new node
//check for NULL
//strcpy word into node
node *new_node = malloc(sizeof(node));
if (new_node == NULL)
{
printf("Not enough memory for malloc");
return false;
}
strcpy(new_node->word,expression);
new_node->next = NULL;
//4: hash word to obtain a hash value
//use hash function
//this will return an index (alphabet-index)
//5: insert node into hash table at that locatíon
//index into hashtable to get linkedlist that you want to add word into
//set pointers to correct order!!!
//first point from new_node to node-number1 and then from head to new_node to not "lose" the list
new_node->next = table[hash(expression)];
table[hash(expression)] = new_node;
}
//first: allocate memory for new node
// node *n = malloc(sizeof(node));
// strcpy(n->word,"HELLO") --> change to different from hello
// n->next = NULL
//load all words from dict into a hash table
//stop when node->next == NULL
//array of linked lists (each of which represents an char (a,b,c,d,...))
//need to use datatype "node"
//needs hash function
//takes word (e.g. "apple") and outputs,which is the starting char
// return true if successfully loaded into memory
fclose(dict);
return true;
}
解决方法
编辑:我发现,我可以在散列函数中使用 tolower() 来解决问题。但老实说,我不知道为什么这现在有效......
unsigned int hash(const char *word)
{
//make it deterministic
//use Hash Function from source
unsigned hashval;
for (hashval = 0; *word != '\0'; word++)
{
hashval = tolower(*word) + 31 * hashval;
}
return hashval % N;
//SOURCE: https://stackoverflow.com/questions/7666509/hash-function-for-string
}