在 Linux 上使用 C 检查目录是否为空
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/6383584/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Check if a directory is empty using C on Linux
提问by freethinker
Is this the right way of checking whether a directory is empty or not in C? Is there a more efficient way to check for an empty directory, especially if it has 1000s of files if not empty?
这是在 C 中检查目录是否为空的正确方法吗?有没有更有效的方法来检查空目录,特别是如果它有 1000 个文件(如果不是空的)?
int isDirectoryEmpty(char *dirname) {
int n = 0;
struct dirent *d;
DIR *dir = opendir(dirname);
if (dir == NULL) //Not a directory or doesn't exist
return 1;
while ((d = readdir(dir)) != NULL) {
if(++n > 2)
break;
}
closedir(dir);
if (n <= 2) //Directory Empty
return 1;
else
return 0;
}
If its an empty directory, readdir
will stop after the entries '.' and '..' and hence empty if n<=2
.
如果它是一个空目录,readdir
将在条目 '.' 之后停止。和 '..' 因此是空的 if n<=2
。
If its empty or doesn't exist, it should return 1, else return 0
如果它为空或不存在,则应返回 1,否则返回 0
Update:
更新:
@c$ time ./isDirEmpty /fs/dir_with_1_file; time ./isDirEmpty /fs/dir_with_lots_of_files
0
real 0m0.007s
user 0m0.000s
sys 0m0.004s
0
real 0m0.016s
user 0m0.000s
sys 0m0.008s
Why does it take longer to check for a directory with lots of files as compared to one with just one file?
为什么与只有一个文件的目录相比,检查包含大量文件的目录需要更长的时间?
采纳答案by cnicutar
Is there a more efficient way to check for an empty directory, especially if it has 1000s of files if not empty
有没有更有效的方法来检查空目录,特别是如果它有 1000 个文件,如果不是空的
The way you wrote your code it doesn't matter how many files it has (you break
if n > 2). So your code is using a maximum of 5 calls. I don't think there's any way to (portably) make it faster.
您编写代码的方式与它有多少个文件无关(break
如果 n > 2,则为您)。所以你的代码最多使用 5 个调用。我认为没有任何方法可以(可移植地)使其更快。
回答by Dawson
bool has_child(string path)
{
if(!boost::filesystem::is_directory(path))
return false;
boost::filesystem::directory_iterator end_it;
boost::filesystem::directory_iterator it(path);
if(it == end_it)
return false;
else
return true;
}
回答by kato2
Maybe this code could help you:
也许此代码可以帮助您:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char *argv[]) {
char *cmd;
char *folder = "/tmp";
int status, exitcode;
char *format="test $(ls -AU \"%s\" 2>/dev/null | head -1 | wc -l) -ne 0";
clock_t start, stop;
int size;
if(argc == 2)
folder = argv[1];
size = strlen(format)+strlen(folder)+1;
cmd = malloc(size * sizeof(char));
snprintf(cmd, size, format, folder);
printf("executing: %s\n", cmd);
status = system(cmd);
exitcode = WEXITSTATUS(status);
printf ("exit code: %d, exit status: %d\n", exitcode, status);
if (exitcode == 1)
printf("the folder is empty\n");
else
printf("the folder is non empty\n");
free(cmd);
return 0;
}
I check if the folder is empty using ls -AU folder 2>/dev/null | head -1 | wc -l, to count the files in the folder, if it returns zero the folder is empty else the folder is non empty. The WEXITSTATUS macro, returns the exit code of the executed command. head command doesn't wait until ls finish, just until the condition is fit.
我使用 ls -AU folder 2>/dev/null | 检查文件夹是否为空 头-1 | wc -l,计算文件夹中的文件数,如果返回零,则该文件夹为空,否则该文件夹为非空。WEXITSTATUS 宏,返回已执行命令的退出代码。head 命令不会等到 ls 完成,直到条件合适。
some examples using the find command to generate long file list show that it is really effective
一些使用 find 命令生成长文件列表的例子表明它确实有效
Command without head
无头命令
/usr/bin/time -p -v find / -print | wc -l
output
Command being timed: "find / -print"
User time (seconds): 0.63
System time (seconds): 1.28
Percent of CPU this job got: 98%
Elapsed (wall clock) time (h:mm:ss or m:ss): 0:01.94
Average shared text size (kbytes): 0
Average unshared data size (kbytes): 0
Average stack size (kbytes): 0
Average total size (kbytes): 0
Maximum resident set size (kbytes): 6380
Average resident set size (kbytes): 0
Major (requiring I/O) page faults: 0
Minor (reclaiming a frame) page faults: 3419
Voluntary context switches: 7
Involuntary context switches: 140
Swaps: 0
File system inputs: 0
File system outputs: 0
Socket messages sent: 0
Socket messages received: 0
Signals delivered: 0
Page size (bytes): 4096
Files counted: 1043497
Command modified using head
使用 head 修改的命令
/usr/bin/time -p -v find / -print | head -1 | wc -l
Command terminated by signal 13
Command being timed: "find / -print"
User time (seconds): 0.00
System time (seconds): 0.00
Percent of CPU this job got: 100%
Elapsed (wall clock) time (h:mm:ss or m:ss): 0:00.00
Average shared text size (kbytes): 0
Average unshared data size (kbytes): 0
Average stack size (kbytes): 0
Average total size (kbytes): 0
Maximum resident set size (kbytes): 2864
Average resident set size (kbytes): 0
Major (requiring I/O) page faults: 0
Minor (reclaiming a frame) page faults: 136
Voluntary context switches: 1
Involuntary context switches: 0
Swaps: 0
File system inputs: 0
File system outputs: 0
Socket messages sent: 0
Socket messages received: 0
Signals delivered: 0
Page size (bytes): 4096
Files counted: 1
As you can see while the first command without "head" tooks 1.28 seconds for execution the command modified with "head" tooks 0 seconds for execution.
正如您所看到的,第一个没有“head”的命令执行时间为 1.28 秒,而使用“head”修改的命令执行时间为 0 秒。
Moreover if we measure the execution time of the above core, with and without head we have.
此外,如果我们测量上述核心的执行时间,我们有和没有头。
Normal ls:
正常 ls:
/usr/bin/time -p ls -A /var/lib/dpkg/info/
real 0.67
user 0.06
sys 0.06
program without head
无头程序
/usr/bin/time -p ./empty.exe /var/lib/dpkg/info/
executing: test $(ls -AU "/var/lib/dpkg/info/" 2>/dev/null | wc -l) -ne 0
exit code: 0, exit status: 0
the folder is non empty
real 0.01
user 0.00
sys 0.01
program using head
使用 head 的程序
/usr/bin/time -p ./empty.exe /var/lib/dpkg/info/
executing: test $(ls -AU "/var/lib/dpkg/info/" 2>/dev/null | head -1 | wc -l) -ne 0
exit code: 0, exit status: 0
the folder is non empty
real 0.00
user 0.00
sys 0.00
Note: if the folder doesn't exists, or you don't have the correct permissions to access it, this program must print "the folder is empty".
注意:如果文件夹不存在,或者您没有正确的访问权限,该程序必须打印“文件夹为空”。
The program was built using: gcc empty.c -o empty.exe
该程序是使用以下方法构建的:gcc empty.c -o empty.exe