如何从我的C或c++代码中确定目录中的文件列表?

我不允许在程序中执行ls命令并解析结果。


当前回答

根据herohuyongtao的帖子和其他一些帖子:

http://www.cplusplus.com/forum/general/39766/

FindFirstFile的预期输入类型是什么?

如何将wstring转换为字符串?

这是一个Windows解决方案。

因为我想要传入std::string并返回一个字符串向量,所以我必须进行一些转换。

#include <string>
#include <Windows.h>
#include <vector>
#include <locale>
#include <codecvt>

std::vector<std::string> listFilesInDir(std::string path)
{
    std::vector<std::string> names;
    //Convert string to wstring
    std::wstring search_path = std::wstring_convert<std::codecvt_utf8<wchar_t>>().from_bytes(path);
    WIN32_FIND_DATA fd;
    HANDLE hFind = FindFirstFile(search_path.c_str(), &fd);
    if (hFind != INVALID_HANDLE_VALUE) 
    {
        do 
        {
            // read all (real) files in current folder
            // , delete '!' read other 2 default folder . and ..
            if (!(fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) 
            {
                //convert from wide char to narrow char array
                char ch[260];
                char DefChar = ' ';
                WideCharToMultiByte(CP_ACP, 0, fd.cFileName, -1, ch, 260, &DefChar, NULL);
                names.push_back(ch);
            }
        } 
        while (::FindNextFile(hFind, &fd));
        ::FindClose(hFind);
    }
    return names;
}

其他回答

2017年更新:

在c++ 17中,现在有一种官方的方法来列出文件系统中的文件:std::filesystem。下面是Shreevardhan给出的一个很好的答案:

# include <字符串> # include < iostream > # include <文件> 命名空间fs = std::filesystem; int main () { Std::string path = "/path/to/directory"; For (const auto & entry: fs::directory_iterator(path)) Std::cout << entry.path() << Std::endl; }

旧的回答:

在小而简单的任务中,我不使用boost,我使用direct .h。它可以作为UNIX中的标准标头使用,也可以通过Toni Ronkko创建的兼容层用于Windows。

DIR *dir;
struct dirent *ent;
if ((dir = opendir ("c:\\src\\")) != NULL) {
  /* print all the files and directories within directory */
  while ((ent = readdir (dir)) != NULL) {
    printf ("%s\n", ent->d_name);
  }
  closedir (dir);
} else {
  /* could not open directory */
  perror ("");
  return EXIT_FAILURE;
}

它只是一个小的头文件,做了大部分你需要的简单的事情,而不使用像boost这样的基于模板的大方法(无意冒犯,我喜欢boost!)

基于上面的答案

#include <vector>
#include <string>
#include <algorithm>

#ifdef _WIN32
#include <windows.h>
std::vector<std::string> files_in_directory(std::string path)
{
    std::vector<std::string> files;

    // check directory exists
    char fullpath[MAX_PATH];
    GetFullPathName(path.c_str(), MAX_PATH, fullpath, 0);
    std::string fp(fullpath);
    if (GetFileAttributes(fp.c_str()) != FILE_ATTRIBUTE_DIRECTORY)
        return files;

    // get file names
    WIN32_FIND_DATA findfiledata;
    HANDLE hFind = FindFirstFile((LPCSTR)(fp + "\\*").c_str(), &findfiledata);
    if (hFind != INVALID_HANDLE_VALUE)
    {
        do 
        {
            files.push_back(findfiledata.cFileName);
        } 
        while (FindNextFile(hFind, &findfiledata));
        FindClose(hFind);
    }

    // delete current and parent directories
    files.erase(std::find(files.begin(), files.end(), "."));
    files.erase(std::find(files.begin(), files.end(), ".."));

    // sort in alphabetical order
    std::sort(files.begin(), files.end());

    return files;
}
#else
#include <dirent.h>
std::vector<std::string> files_in_directory(std::string directory)
{
    std::vector<std::string> files;

    // open directory
    DIR *dir;
    dir = opendir(directory.c_str());
    if (dir == NULL)
        return files;

    // get file names
    struct dirent *ent;
    while ((ent = readdir(dir)) != NULL)
        files.push_back(ent->d_name);
    closedir(dir);

    // delete current and parent directories
    files.erase(std::find(files.begin(), files.end(), "."));
    files.erase(std::find(files.begin(), files.end(), ".."));

    // sort in alphabetical order
    std::sort(files.begin(), files.end());

    return files;
}
#endif  // _WIN32

我认为,下面的代码片段可以用来列出所有的文件。

#include <stdio.h>
#include <dirent.h>
#include <sys/types.h>

int main(int argc, char** argv) { 
    list_dir("myFolderName");
    return EXIT_SUCCESS;
}  

static void list_dir(const char *path) {
    struct dirent *entry;
    DIR *dir = opendir(path);
    if (dir == NULL) {
        return;
    }

    while ((entry = readdir(dir)) != NULL) {
        printf("%s\n",entry->d_name);
    }

    closedir(dir);
}

这是使用的结构(出现在direct .h中):

struct dirent {
    ino_t d_ino; /* inode number */
    off_t d_off; /* offset to the next dirent */
    unsigned short d_reclen; /* length of this record */
    unsigned char d_type; /* type of file */
    char d_name[256]; /* filename */
};

为什么不使用glob()?

#include <glob.h>

glob_t glob_result;
glob("/your_directory/*",GLOB_TILDE,NULL,&glob_result);
for(unsigned int i=0; i<glob_result.gl_pathc; ++i){
  cout << glob_result.gl_pathv[i] << endl;
}

这对我很管用。它用所有文件的名称(没有路径)写入一个文件。然后它读取txt文件并为你打印出来。

void DisplayFolderContent()
    {

        system("dir /n /b * > file_names.txt");
        char ch;
        std::fstream myStream("file_names.txt", std::fstream::in);
        while (myStream.get(ch))
        {
            std::cout << ch;
        }

    }