我正在尝试将文件中的唯一字符串写入链接列表,并增加每个重复单词的计数。我想使用 getNextWord 函数返回指向文件中下一个单词的指针。问题是我对 c 和指针非常陌生,所以我实际上不知道在我的 main 方法中要做什么来调用 getNextWord 以及如何使用这个字符串指针来实际访问它所指向的字符串。那么如何使用我的函数来获取需要作为节点键的字符串呢?另外,任何其他建议将不胜感激,如果您发现我的函数或结构有任何问题,请告诉我!非常感谢您的宝贵时间。这是我的函数和结构..
#define MAX_WORD_LEN 256
struct list {
int count;
char string[MAX_WORD_LEN];
struct list *next;
};
char* getNextWord(FILE* fd) {
char c;
char wordBuffer[MAX_WORD_LEN];
int putChar = 0;
while((c = fgetc(fd)) != EOF) {
if(isalnum(c)) break;
}
if (c == EOF) return NULL;
wordBuffer[putChar++] = tolower(c);
while((c = fgetc(fd)) != EOF) {
if(isspace(c) || putChar >= MAX_WORD_LEN -1) break;
if(isalnum(c)) {
wordBuffer[putChar++] = tolower(c);
}
}
wordBuffer[putChar] = '\0';
return strdup(wordBuffer);
}
最佳答案
我发现您的列表节点定义与从文件中检索单词的函数之间存在细微差异。
在 C 语言中,您完全负责内存分配,因此您必须决定谁将分配数据以及谁将释放它们。
这里你的文件解析函数进行分配。这意味着 getNextWord
返回的指针将引用必须在某个时刻释放的动态内存。
同时,您的节点结构保存另一个内存缓冲区,用于表示同一段数据。
在当前的实现中,您必须将通过 getNextWord
获取的字符串复制到节点中,然后释放该字符串,如下所示:
char * new_word = getNextWord (file);
strcpy (my_node->string, new_word);
free (new_word );
这浪费时间和资源:每个字符都会被复制两次(一次在 getNextWord
中,另一次在 strcpy
中)。
为了避免重复,您基本上可以做两件事。
1) 将 string
字段更改为 char *
以保留对 getNextWord
结果的引用
struct list {
int count;
char * string; // <- reference to the string allocated by getNextWord
struct list *next;
};
// populating node
my_node->string = getNextWord (file);
在这种情况下,每个节点都负责最终释放字符串。
2) 将string
保留为字符缓冲区,并让getNextWord
直接填充它
typedef char wordBuffer_t[MAX_WORD_LEN];
struct list {
int count;
wordBuffer_t string; // <- storage for the word inside each node
struct list *next;
};
char* getNextWord(FILE* fd, wordBuffer_t wordBuffer) {
// rest of the code does not change
// populating node
getNextWord (file, my_node->string);
在这种情况下,不需要动态分配。另一方面,每个节点需要为尽可能大的字符串分配足够的空间,这在内存消耗方面效率很低。
作为一个重要的旁注,我建议您在使用任何可能用作函数参数的数组时系统地使用 typedef(这里 wordBuffer_t
被传递给 getNextWord
) >).
它将使您的代码更具可读性,并将您从 this common C pitfall 中拯救出来。
关于c - 如何使用字符串指针访问字符串的其余部分?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21655127/