struct stat info在循环中不更新,给出可笑的修改日期



对于代码的一部分,我需要将给定目录中每个文件的名称和统计信息(用户ID、组ID、修改时间、权限等)保存到一个自定义结构的数组中。将信息保存到数组中是可以的,所以为了清楚起见,我把这些东西省略了。我遇到的问题是预定义的struct stat:在测试中,它为目录中的每个文件打印出相同的确切修改日期,这是一个问题,而日期来自1969,这是另一个问题(考虑到我清楚地记得去年某个时候创建和修改了这些文件)。我不确定哪里出了问题;如能得到帮助,将不胜感激。

注意:这是我第一次用C编程,所以如果有任何明显的错误,请告诉我。我的教授非常热衷于独立研究,并没有涵盖所有需要知道的重要事情。此外,我意识到我需要检查错误——这些检查已经写好了,将在稍后实现。在我担心所有的错误检查之前,我只需要修复这段代码的晴天部分,所以请不要告诉我这是我的问题。我总是给它一个简单易懂的目录。它应该没有问题打开或阅读。

  int main ()
  {
        DIR *myDIR;
        struct dirent *mydirent = malloc(sizeof(struct dirent));        //necessary?
        struct stat mystat;
        myDIR = opendir(pathname);
        int count = 0;
        while ((mydirent = readdir(myDIR)) != NULL)
             count++;
        rewinddir(myDIR);
        struct file_info **file_info_array = malloc(sizeof(struct file_info*)*(count+1));
        int i = 0;
        while ((mydirent = readdir(myDIR)) != NULL)
        {
             stat(mydirent->d_name, &mystat);
             printf("name: %sn", mydirent->d_name);
             printf("mod_time: %sn", ctime(&mystat.st_mtime));
             /*
             ... saving file info into file_info_array
             */
        }
        int is_closed = closedir(myDIR);
        /*
        ... freeing pointers
        */
        return 0; 
  }

将评论转换为答案

您没有检查stat()是否成功;你不能推迟错误检查——这是不理智/不安全的。如果失败,则不能保证stat结构的内容是合理的。你还没有展示pathname是如何设置的。如果pathname不是.(或.的同义词),那么stat()调用失败;您需要将readdir()返回的名称转换为相对于pathname的名称—例如:

char path[PATH_MAX];    /* <limits.h> - if it is defined at all */
snprintf(path, sizeof(path), "%s/%s", pathname, mydirent->d_name);
if (stat(path, &mystat) == 0)
{
    …go ahead with printing, etc…
}

哦,天哪,这就是原因!它需要是一个完整的路径吗?这是有道理的,但由于某些原因,当其他同学编码它时,他们按照我最初的方式实现它,即mydirent->d_name,并且没有问题。我想知道为什么?

不一定是完整路径;只是一条可以找到的路。如果您只执行stat(mydirent->d_name, &mystat),那么您将在当前目录中查找具有给定名称的文件—而不是读取该名称的目录(除非该目录恰好是.)。也许同学用的是chdir(pathname) ?或者他们只使用.(或.的同义词)作为路径名?

那么,它是如何成功地打印出所有的名称,即使它们只存在于输入目录中,而不是我当前的目录中?我不是想和你争论;我只是真的很好奇stat()dirent是如何工作的。

readdir()读取名称(仅;没有路径信息)从pathname命名的目录。所以它可以被打印出来。一般来说,stat()会失败,因此您会得到垃圾来打印从中获得的信息。

John Bollinger评论:

另一方面,不,没有必要仅仅因为声明了一个可以指向struct dient的变量就为它设置malloc()空间。在安全地解除对变量的引用之前,确实需要给它赋一个有效值,但是可以通过赋readdir()的返回值来实现,假设readdir()成功。-

正如John Bollinger所说,malloc()是不必要的,更糟糕的是,它是一个内存泄漏。

最新更新