赞
踩
在Linux下,需要实现某个目录下文件的遍历的时候,可以使用opendir,readdir,closedir这些接口。这些接口使用说明如下所示:
1).opendir
DIR* opendir(const char * name);
#include <sys/types.h>
#include <dirent.h>
DIR *opendir(const char *name);
传入name路径,成功则返回非空DIR指针,否则返回NULL; 注意DIR前面没有struct,如果加上编译器会warning。
2).readdir
struct dirent *readdir(struct DIR* dir);
readdir一般要配合opendir使用,readdir不是线程安全函数,代替他的有readdir_r。
readdir返回 struct dirent *指针,读完目录下所有文件时,返回NULL。
3).closedir
void closedir(DIR* dir); 关闭打开的目录描述符dir,同时释放dir空间。Closedir需要配合opendir使用。
下面简单记录下这些接口的使用例子,主要涉及文件遍历,文件查找,文件模糊查找,文件删除,关键字查找并删除等功能。
1.首先在Linux系统下,在这里创建一个命名为"proj"测试的工程。
2.创建一个名为“dirtest.c”的源文件,粘贴如下所示的内容:
- #include<stdio.h>
- #include<stdlib.h>
- #include <stdarg.h>
- #include <sys/types.h>
- #include <dirent.h>
- #include<string.h>
-
- //定义一些文件操作的宏
- #define MODE_LIST_ALL_FILE 0 //列出所有文件
- #define MODE_FIND_FILE 1 //查找一个文件
- #define MODE_DELETE_FILE 2 //删除一个文件
- #define MODE_FUZZY_SEARCH_FILE 3 //通过关键字匹配查找文件
- #define MODE_FUZZY_SEARCH_DELETE_FILE 4 //通过关键字匹配查找并删除文件
-
- /*
- 函数功能:列出该目录下的所有文件
- */
- void list_all_files(DIR *dir)
- {
- int index=0;
- struct dirent *d;
- while ((d = readdir(dir)) != NULL)
- {
- index++;
- LOG("[index %d]:%s\n", index, d->d_name);
- }
-
- }
- /*
- 函数功能:查找文件
- 返回:1,成功找到;0:未找到文件
- */
-
- int find_files(DIR *dir, char *file)
- {
- struct dirent *d;
- int find = 0;
- while ((d = readdir(dir)) != NULL)
- {
- //如果名称匹配上,则打印出该文件名称提示
- if(!strcmp(d->d_name, file)) {
- LOG("Locate the file named%s\n", d->d_name);
- find = 1;//返回结果置1
- }
- }
- return find;
- }
- /*
- 函数功能:通过关键字匹配查找文件
- 返回:1,成功找到;0:未找到文件
- */
-
- int fuzzy_search_files(DIR *dir, char *keyword)
- {
- struct dirent *d;
- int find = 0;
- while ((d = readdir(dir)) != NULL)
- {
- //如果名称匹配上,则打印出该文件名称提示
- if(strstr(d->d_name, keyword)) {
- LOG("file :%s match!!!\n", d->d_name);
- find = 1;//返回结果置1
- }
- }
- return find;
- }
-
- /*
- 函数功能:删除一个文件
- 返回:1,成功找到,并删除该文件;0:未找到文件
- */
- int delete_files(DIR *dir, char *test_dir, char *file)
- {
- struct dirent *d;
- int find = 0;
- while ((d = readdir(dir)) != NULL)
- {
- if(!strcmp(d->d_name, file)) {
- char delete_file[64]="";
- sprintf(delete_file, "%s/%s", test_dir, file);//需要将路径+文件名才能正确删除
- unlink(delete_file);
- LOG("delete file:%s success!\n", delete_file);
- find = 1;
- }
- }
- return find;
- }
- /*
- 函数功能:删除通过关键字匹配上的文件
- 返回:1,成功找到,并删除该文件;0:未找到文件
- */
- int delete_files_by_keyword(DIR *dir, char *test_dir, char *keyword)
- {
- struct dirent *d;
- int find = 0;
- while ((d = readdir(dir)) != NULL)
- {
- if(strstr(d->d_name, keyword)) {
- char delete_file[64]="";
- sprintf(delete_file, "%s/%s", test_dir, d->d_name);//需要将路径+文件名才能正确删除
-
- unlink(delete_file);
- LOG("delete file:%s success!\n", delete_file);
- find = 1;
- }
- }
- return find;
- }
- /*
- 函数功能:接收并解析命令行输入的参数
- 返回:无
- */
-
- void dir_proc(char *argv[])
- {
- char *dir_name = argv[1];
- int cmd_code = atoi(argv[2]);
- DIR *dir;
- struct dirent *d;
- dir = opendir(dir_name);
- if (!dir)
- {
- LOG("cannot open dir %s", dir_name);
- return ;
- }
-
- //根据代号,作出不同的操作
- switch(cmd_code) {
- case MODE_LIST_ALL_FILE:
- {
- //显示该目录下的所有文件
- list_all_files(dir);
- break;
- }
- case MODE_FIND_FILE:
- {
- //查找文件
- if(argv[3]) {
- if(!find_files(dir,argv[3])) {
- LOG("file name %s not found!\n", argv[3]);
- }
- }
- else {
- show_help();
- }
- break;
- }
- case MODE_DELETE_FILE:
- {
- //删除文件
- if(argv[3]) {
- if(!delete_files(dir,argv[1], argv[3])) {
- LOG("file name %s not found!delete fail\n", argv[3]);
- }
- }
- else {
- show_help();
- }
- break;
- }
- case MODE_FUZZY_SEARCH_FILE:
- {
- //通过关键字查找文件
-
- if(argv[3]) {
- if(!fuzzy_search_files(dir, argv[3])) {
- LOG("file name search by keywords %s fail!\n", argv[3]);
- }
- }
- else {
- show_help();
- }
- break;
- }
- case MODE_FUZZY_SEARCH_DELETE_FILE:
- {
- //通过关键字查找,并删除文件
- if(argv[3]) {
- if(!delete_files_by_keyword(dir,argv[1], argv[3])) {
- LOG("file name search by keywords %s fail!\n", argv[3]);
- }
- }
- else {
- show_help();
- }
- break;
- }
- default:
- {
- LOG("command unkown!\n");
- break;
- }
- }
- closedir(dir);
- }
3.创建一个名为”main.c”的文件,内容如下所示:
- #include<stdio.h>
- #include<stdlib.h>
- #include <stdarg.h>
- #include <sys/types.h>
- #include <dirent.h>
- #include<string.h>
-
- /*
- 函数功能:日志打印
- */
- void LOG(const char *format,...)
- {
- va_list argptr;
- char buffer[2048];
- va_start(argptr,format);
- vsprintf(buffer,format,argptr);
- va_end(argptr);
-
- printf("%s", buffer);
- }
- /*
- 函数功能:显示菜单选项
- */
- void show_help()
- {
- LOG("Invalid parameter!\n");
- LOG("-h:Show help\n");
- LOG("0:List all files\n");
- LOG("1:Find a file, (for example: ./dirtest test_dir 1 a.txt)\n");
- LOG("2:Delete a file, (for example: ./dirtest test_dir 2 a.txt)\n");
- LOG("3:Fuzzy find file, (for example: ./dirtest test_dir 3 a)\n");
- LOG("4:Delete files by keyword, (for example: ./dirtest test_dir 4 a)\n");
- }
- /*
- 程序入口
- */
- int main(int argc, char *argv[])
- {
- LOG("run dir test!\n");
- if(argc<3) {
- show_help();
- exit(0);
- }
- dir_proc(argv);
- return 0;
- }
4.创建一个编译的Makefile,方便编译整个工程,内容如下所示:
- CPROG = dirtest #生成一个名为dirtest的目标文件
- BIN = $(CPROG)
- CC= gcc
- OBJS=main.o dirtest.o
-
- all: $(BIN)
- clean:
- rm -f $(OBJS) $(BIN)
- $(BIN): $(OBJS)
- $(CC) -o $(BIN) $(OBJS) $(CFLAGS) $(LDFLAGS) $(CFLAGS_EXTRA)
5.创建完dirtest.c,main.c,Makefile后,便可以编译了,在该工程目录下执行make clean;make,编译成功之后会生成一个名为 “dirtest”的可执行文件。如下图所示:
6.测试,在该路径下创建一个名为“test_dir”的目录,然后随意创建一些文件。如下图所示:
6.1列出路径下的所有文件
6.2查找文件
6.3删除文件
6.4关键字查找文件
6.5通过关键字查找,并删除文件
至此,上述功能已简单测试完毕。
总结:关于目录的操作例子就写到这里了,熟悉了这些操作,自然而然地可以自己先ls的命令了。在后续的工作中,如果有遇到针对目录以及里面相关文件的管理操作,就可以在这个例子的基础上进行快速改装了。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。