C语言 递归函数,使用 fork() 遍历目录运行次数过多



我试图通过遍历 C 中的目录来更好地理解分叉进程的概念。

我的函数没有按照我预期的方式工作:我的一些目录和文件被多次访问。

我应该从当前工作目录开始并列出所有文件/文件夹。 每次找到子目录时,我都应该调用 fork(( 并做同样的事情,直到我用尽了每个文件/目录。 我不需要按任何特定顺序访问这些项目,但我确实需要只访问一次每个项目。

我让程序在不使用 fork(( 的情况下递归工作。 但是我不能完全使用 fork(( 正确处理它。 这是函数。 它只是传递字符串".",以在当前工作目录中启动它。

int traverse(char* directory)
{
struct dirent *currentDir;  
DIR *traverser = opendir(directory);
if (traverser == NULL)
{
printf("Error: Could not open directory.n");
return 0;
}
while ((currentDir = readdir(traverser)) != NULL)
{       
if (currentDir->d_type == DT_DIR && strcmp(currentDir->d_name, ".") != 0 && strcmp(currentDir->d_name, "..") != 0)
{
int PID = fork();
forkCount++;
char pathBuffer[1024];
if (PID == 0)
{
snprintf(pathBuffer, sizeof(pathBuffer), "%s/%s", directory, currentDir->d_name);
traverse(pathBuffer);
}
else
{
listOfPIDS[forkCount] = PID;
int status = 0;
wait(&status);
}
}
else if (strcmp(currentDir->d_name, ".") != 0 && strcmp(currentDir->d_name, "..") != 0)
{
printf("%sn", currentDir->d_name);
}
}
closedir(traverser);
return 0;
}

在考虑了其他用户的评论并进行了更多尝试之后,我想出了这个解决方案。 通过在子进程递归调用函数后中断while()循环,不会重新访问相同的文件夹/文件。 正如其他用户在他们的评论中指出的那样,当父级调用 fork 并开始等待时,子级开始并以递归方式再次调用该函数。 一旦孩子的递归调用完成,它就会返回到目录中完全相同的位置,并开始列出所有文件。 完成后,父级完成等待,并返回到完全相同的位置并开始列出文件。 因此,父级和子级都返回到目录中的同一位置并列出文件。 只需在孩子的递归调用完成执行后添加exit(0);就可以解决问题。此外,我将pathBuffer[]forkCount++移到子进程的部分,因为父进程不需要担心这一点。

代码如下:

int traverse(char* directory)
{
struct dirent *currentDir;  
DIR *traverser = opendir(directory);
if (traverser == NULL)
{
printf("Error: Could not open directory.n");
return 0;
}
while ((currentDir = readdir(traverser)) != NULL)
{       
if (currentDir->d_type == DT_DIR && strcmp(currentDir->d_name, ".") != 0 && strcmp(currentDir->d_name, "..") != 0)
{
int PID = fork();
if (PID == 0)
{
forkCount++;        
char pathBuffer[1024];
snprintf(pathBuffer, sizeof(pathBuffer), "%s/%s", directory, currentDir->d_name);
traverse(pathBuffer);
exit(0);
}
else
{
listOfPIDS[forkCount] = PID;
int status = 0;
wait(&status); //wait at end
}
}
else if (strcmp(currentDir->d_name, ".") != 0 && strcmp(currentDir->d_name, "..") != 0)
{
printf("%s: Proc'd by %dn", currentDir->d_name, getpid());
}
}
closedir(traverser);
return 0;
}

相关内容

最新更新