2

我有以下 C 代码:

#include <dirent.h>
#include <stdio.h>
#include <string.h>
#include <signal.h>
#include <unistd.h>


int main(int argc, const char *argv[]){
    const char *directory_path;
    directory_path = argv[1];
    char *dirname;
    dirname = strdup(directory_path);
    recursive_ls(dirname);

}


int recursive_ls(char *dirname){
    printf("%s\n",dirname);
    DIR *d;
    struct dirent *dir;

    if ((d=opendir(dirname))==-1) {
        perror("Oops");
        return(0);
    }
    if(d){
        while((dir = readdir(d)) !=NULL){
            char *dname = dir->d_name;
            puts(dname);
/*          if(strcmp(dir->d_type,DT_REG)){
                puts("I am a regular file");
            } else if(strcmp(dir->d_type,DT_DIR)){
                puts("I am a directory.");
                            recursive_ls(strcat(strcat(dirname,"/"),dir->d_name));
                } else {
                    puts("I am not a file");
            }
*/    
        }

        closedir(d);
    }
return(0);
}

如果我注释掉if(){} else if(){} else(){}while 循环内部,我会得到以下输出:

Debug
.project
pipe_test.c
.
..

这是目录中的所有内容。另一方面,如果我取消注释它,那么我会得到以下信息:

/home/wilbert/workspace/pipe_test
.cproject

我想如果递归步骤搞砸了一切,我至少应该得到“我不是文件”部分;但是,由于某种原因,我没有,所以我很困惑。这个东西编译并且没有显示语法错误,所以我真的很困惑。为什么会这样?

4

2 回答 2

4

正如 Jonathon 建议d_type的那样unsigned char,因此更改为:

if(dir->d_type == DT_REG){
   puts("I am a regular file");
} else if(dir->d_type == DT_DIR){
   puts("I am a directory.");
   recursive_ls(strcat(strcat(dirname,"/"),dir->d_name));
} else {
   puts("I am not a file");
}
于 2013-10-19T06:58:49.333 回答
2

d_type成员struct dirent不是字符串 ( char *),而是unsigned char. 这实际上只是一个 8 位整数,是原始类型。在比较原始类型时,我们使用==运算符。strcmp严格用于比较字符串。

if (dir->d_type == DT_REG) {
   puts("I am a regular file");
} else if (dir->d_type == DT_DIR) {
   puts("I am a directory.");
   recursive_ls(strcat(strcat(dirname,"/"),dir->d_name));
} else {
   puts("I am not a file");
}

有关更多信息,请参阅手册

而且,即使您的原始代码编译时没有错误,当您包含注释主体时,它也会发出很多警告。一个好的提示是始终将编译器警告视为错误。

于 2013-10-19T07:04:06.763 回答