段错误 11 - 在 C 中查找文件中的单词

Segmentation Fault 11 - Finding Words in File in C

我有一个使用 findMatches 函数打开和读取的 .txt 文件。该文件具有以下结构:

Auckland link42 link24 link23 link5
Wellington link3 link21
Queenstown link1 link9 link15

请求数组包含用户输入的关键字。我试图只打印与请求中的单词相对应的标记。

例如:

>>> Auckland Wellington

Auckland
link42
link24
link23
link5

Queenstown
link1
link9
link15

但是,我得到了 Segmentation Fault 11。如果搜索 1 个关键字,则不会出现错误,但只有在搜索 3 个或更多关键字时才会出现错误,并且它只显示最多两个具有相应链接的关键字(如上)。

为什么会发生这种情况,我该如何解决?

#define MAXSTR 1000

int findMatches (const char *filename, char *request[], int size) {

    char lines[MAXSTR];
    char delim[2] = " ";
    char *token;

    FILE *file; 

    if ((file = fopen(filename, "r")) == NULL) {
        printf("Error.\n");
    }

    while(fgets(lines, MAXSTR, file) != NULL) {
        token = strtok(lines, delim);
    
        for (int i = 0; i < size; i++) {
            if (!strcmp(request[i], token)) {
                
                    while (token != NULL) {
                        printf("%s\n", token);
                        token = strtok(NULL, delim); 
                }
            }
        }
    }
    return 0;
}


int main (int agrc, char *argv[]) {

    char *request[MAXSTR];
    int size = agrc - 1;
    int index = 0;

    for (int i = 1; i < agrc; i++) {
        request[index] = argv[i];
        index++;
    }

    findMatches("index.txt", request, size);

    return 0;
}

在这个循环中

        token = strtok(lines, delim);
    
        for (int i = 0; i < size; i++) {
            if (!strcmp(request[i], token)) {
                
                    while (token != NULL) {
                        printf("%s\n", token);
                        token = strtok(NULL, delim); 
                }
            }
        }

当请求第一次匹配token时,执行while循环,然后token变为NULL。然后,for 循环的下一次迭代,strcmp(request[i], NULL) 被执行,这导致了分段错误。

您应该在 while 循环之后添加 break; 以避免这种情况。

        token = strtok(lines, delim);
    
        for (int i = 0; i < size; i++) {
            if (!strcmp(request[i], token)) {
                
                    while (token != NULL) {
                        printf("%s\n", token);
                        token = strtok(NULL, delim); 
                }
                break; /* you should add this */
            }
        }

此外,当 fileNULL 时,您不应该执行 fgets(lines, MAXSTR, file)

    if ((file = fopen(filename, "r")) == NULL) {
        printf("Error.\n");
        return -1; /* you should add this */
    }

而且您忘记关闭打开的文件。

    }
    fclose(file); /* you should add this */
    return 0;
}