以下代码打开一个路径并递归读取目录并打印其中的文件。目前它只打印目录的路径,然后打印其中的每个文件,但我想实现一个链接列表,其中包含1个char *变量,其中包含每个访问过的文件的完整路径。
以下是代码:
#include <dirent.h>
#include <stdio.h>
#include <string.h>
void show_dir_content(char * path)
{
DIR * d = opendir(path);
if(d==NULL) return;
struct dirent * dir;
while ((dir = readdir(d)) != NULL)
{
if(dir-> d_type != DT_DIR) // if the type is not directory just print it
printf("\t%s\n",dir->d_name);
else
if(dir -> d_type == DT_DIR && strcmp(dir->d_name,".")!=0 && strcmp(dir->d_name,"..")!=0 ) // if it is a directory
{
char d_path[255]; // here I am using sprintf which is safer than strcat
sprintf(d_path, "%s/%s", path, dir->d_name);
printf("%s\n",d_path);
show_dir_content(d_path);
}
}
closedir(d);
}
int main(int argc, char **argv)
{
show_dir_content(argv[1]);
return(0);
}
用于链表的结构可以非常简单,例如:
typedef struct search search;
struct search {
char *path;
char *fileName;
char *fullPathToFile;
search *next;
};
我很难将malloc用于结构并在递归函数中创建实际的链表。任何帮助表示赞赏。
答案 0 :(得分:1)
每次找到文件时都需要创建一个新的search
节点。填写新节点,然后将其添加到列表末尾。
const char *path_format = "%s/%s";
// Modified to take a node ptr. This should be the last node in the list
// Returns a node ptr. This is the new last node in the list
search * show_dir_content(char * path, search *node)
{
DIR * d = opendir(path);
if(d==NULL) return node;
struct dirent * dir;
while ((dir = readdir(d)) != NULL)
{
if(dir-> d_type != DT_DIR) {
// Found a file. Alloc a new search node and fill in
// (TODO: You should check the return from malloc for failure)
search *new_node = malloc(sizeof(search));
// TODO: copy all the names. Hint: strdup
new_node->next = NULL;
// Append to end of list
node->next = new_node;
// Update node pointer to now point to the new node
node = node->next;
}
else
if(dir -> d_type == DT_DIR && strcmp(dir->d_name,".")!=0 && strcmp(dir->d_name,"..")!=0 ) // if it is a directory
{
// Not sure 255 chars will be enough....
char d_path[255]; // here I am using sprintf which is safer than strcat
sprintf(d_path, path_format, path, dir->d_name);
printf("%s\n",d_path);
// Make sure you update the node pointer to reflect any
// changes made in the recursive call
node = show_dir_content(d_path, node);
}
}
closedir(d);
// Return the last node (this may be same as input parameter if no files found
return node;
}
更新main
以创建根节点并将其传递给函数
int main(int argc, char **argv)
{
search root = {0};
show_dir_content(argv[1], &root);
// Note that root is a dummy node.
// The list actually begins at root->next
// Also, before you exit, free all mem
search *node = root.next, *next;
while (NULL != node) {
free(node->path);
free(node->fileName);
free(node->fullPathToFile);
next = node->next;
free(node);
node = next;
}
return(0);
}
答案 1 :(得分:0)
我认为你可以修改你的原型,添加一个struct search *
param,它将成为你名单上的头脑。
当你需要在你的列表中放置一个元素时,只需在队列中添加一个节点(或者如果你想要在头部添加一个节点,但你需要一个struct search **
而不是一个简单的指针。
然后,当你需要放置一个元素时,只需调用一个能够创建一个元素的函数并将它放在你想要的位置。
在那之后,你将只给每个递归调用你的列表的head ptr