linux 遍历目录+文件(优化版本)

时间:2023-03-09 15:18:48
linux 遍历目录+文件(优化版本)

c++17 filesystem, regex 遍历目录


#include <stdio.h> #include <sys/types.h>
#include <dirent.h>
#include <sys/stat.h> #include <sys/time.h> //linux 精确度s, us gettimeofday() #include <iostream>
#include <string>
#include <vector>
using namespace std; //char filename[512]; std::vector<string> vecFilePath;
std::vector<string> vecFilename; int isDirectory(string fullpath)
{
struct stat st;
int ret = stat(fullpath.c_str(), &st);//return -1, if failed
if(ret==0)//ok
{
if(S_ISDIR( st.st_mode))//是文件目录
{
//cout<<"S_ISDIR:"<<fullpath<<endl;
return 1;
}
else if(S_ISREG (st.st_mode) ) //是文件
{
//cout<<"S_ISREG:"<<fullpath<<endl;
return 0;
}
} return -1;//failed
} int TraverseDir(string path, bool isNeedFilterFlag, vector<string> vecSuffix,bool isTraveSubDirFlag)
{
DIR *d; //声明一个句柄
struct dirent *file; //readdir函数的返回值就存放在这个结构体中 if(!(d = opendir(path.c_str())))
{
cout<< "error opendir:"<<path<<endl;
return -1;
} while((file = readdir(d)) != NULL)
{
string strFileName(file->d_name); //隐藏文件.a.txt 隐藏目录.folderA, 没做处理,可以被找到。 //忽略 当前目录. 和上一级目录..
//if(strcmp(file->d_name, ".") == 0 || strcmp(file->d_name, "..") == 0)
if(strFileName.compare(".")==0 || strFileName.compare("..")==0)
{
continue;
} string fullPath = path + "/" + strFileName;// path+"//"+strFileName; 也OK int ret = isDirectory(fullPath);
if(ret==0)//是文件
{
if(isNeedFilterFlag==true)//需要过滤
{ bool isNeedSuffix(0);
for(uint32_t i =0; i< vecSuffix.size(); i++)
{
string fileSuffix = fullPath.substr(fullPath.length() - vecSuffix.at(i).length());
bool bMatch = fileSuffix.compare(vecSuffix.at(i))==0;
isNeedSuffix = isNeedSuffix || bMatch;
} if(isNeedSuffix)
{
vecFilename.push_back(strFileName);
// vecFilename.push_back(fullPath);
}
}
else
{
vecFilename.push_back(strFileName);
}
}
else if(ret==1)//是目录
{
if(isTraveSubDirFlag==true)//如果需要可以继续遍历
{
TraverseDir(fullPath, isNeedFilterFlag, vecSuffix, isTraveSubDirFlag);
} //continue;
}
else //stat() return -1, failed
{
continue;
} }
closedir(d);
return 0;
}
int main()
{
string strPath("/home/scott/project"); // /home/scott/project/data vector<string> vecSuffix;
vecSuffix.push_back(".jpg");
vecSuffix.push_back(".png"); vecSuffix.push_back(".aac");
vecSuffix.push_back(".mp3");
vecSuffix.push_back(".wma");
vecSuffix.push_back(".wave"); vecSuffix.push_back(".mp4");
vecSuffix.push_back(".rmvb");
vecSuffix.push_back(".rmvb");
vecSuffix.push_back(".mov");
vecSuffix.push_back(".flv");
vecSuffix.push_back(".ts"); bool isNeedFilterFlag(true);//过滤文件类型
bool isTraveSubDirFlag(true);//false struct timeval tvBegin,tvEnd;
struct timezone tz; gettimeofday (&tvBegin , &tz);
TraverseDir(strPath, isNeedFilterFlag, vecSuffix, isTraveSubDirFlag);
gettimeofday (&tvEnd , &tz); uint64_t SpendTime = (tvEnd.tv_sec-tvBegin.tv_sec)*1000+(tvEnd.tv_usec-tvBegin.tv_usec)/1000; std::cout<< "tvBegin.tv_sec ="<<tvBegin.tv_sec << ".tvBegin.tv_usec ="<< tvBegin.tv_usec<<std::endl;
std::cout<< "tvEnd.tv_sec ="<<tvEnd.tv_sec << ".tvEnd.tv_usec ="<< tvEnd.tv_usec <<std::endl;
std::cout<< "SpendTime="<<SpendTime<<"ms"<<std::endl; cout<<"find number:"<<vecFilename.size()<<endl; /*
for(int i = 0; i < vecFilename.size(); i++)
{
cout<< vecFilename.at(i)<<endl;
}*/ return 0;
}