c ++列出(LINUX)中的所有目录和子目录

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/9138866/
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

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-06 04:22:35  来源:igfitidea点击:

c++ list all directories and subdirectories within in (LINUX )

c++linuxubuntudirectory

提问by ioan paul

I am new in c ++ . could someone please give me some code of how to get all directories and all it's subdirectories RECURSIVELY in LINUX. i haven't found anything on internet that could help me ( or code that works.) I need to get all files withing folder and it;s subfolder.

我是 C++ 新手。有人可以给我一些关于如何在 LINUX 中递归获取所有目录及其所有子目录的代码。我还没有在互联网上找到任何可以帮助我的东西(或有效的代码)。我需要获取文件夹及其子文件夹中的所有文件。

IN UBUNTU I don't have getfiles, directories...

在 UBUNTU 中,我没有 getfiles、目录...

回答by Basile Starynkevitch

In addition of Dmitri's answer, you might be interested in using the nftwlibrary function which "does the recursion for you"

除了Dmitri 的回答之外,您可能对使用“为您进行递归”的nftw库函数感兴趣

回答by osirisgothra

The answers on listing directories are only the first part of the answer but i didnt see anyone answering the recursive part. To recursively do anything you have to create a subroutine that "calls itself" -- note that you should take care when dealing with symbolic links especially in cases like /exports when using nfs, that could lead to circular recursion and lock you in an infinte loop! Basically:

列出目录的答案只是答案的第一部分,但我没有看到有人回答递归部分。要递归地做任何事情,您必须创建一个“调用自身”的子例程——请注意,在处理符号链接时应该小心,尤其是在使用 nfs 时 /exports 等情况下,这可能会导致循环递归并将您锁定在无限期环形!基本上:

this isn't real code, its pseudo-code to try to help you get a better idea of how the recursion works without confusing you with language this idea can be applied in any language that has some sort of call-return mechanism which these days is just about every language i can think of

这不是真正的代码,它的伪代码试图帮助您更好地了解递归的工作原理,而不会混淆您的语言这个想法可以应用于具有某种调用返回机制的任何语言中几乎是我能想到的每一种语言

// PSEUDO-CODE
stiring entriesarray[] myfunc(string basedir)
{
  string results[] = getfilesandfolders(basedir) // you might want to specify a filter
  for each string entry in results
  {
        // if you want only files you'll need to test for if entry is a file
       entriesarray.add(entry)
       if (entry is a directory && entries is not a symbolic link)
       {
            string moreentriesarray[] = myfunc(entry)
            entriesarray.join(moreentriesarray)
       }
  }
  return entriesarray[]
}

notice how if the entries do not contain any real directories, the function doesn't call itself? this is important because this is how infinite recursion is avoided. Be warned however you might want to make it so this operation can be cancelled, larger filesystems these days can take a lot of time to process. The way I usually do it is to start another thread and do the search in the background, and have the background thread check for a cancellation flag in case the user wants to stop the operation, and so it can post information about how much time is left, percentage complete, etc ,etc. its a bit crude but this should get anyone interested in this type of thing going in the right direction. And remember to ALWAYS properly check for errors and place exception handling, this is something that I see new programmers skip ALL the time.

注意如果条目不包含任何实际目录,函数不会调用自身?这很重要,因为这是避免无限递归的方式。但是请注意,您可能想要取消此操作,现在较大的文件系统可能需要大量时间来处理。我通常这样做的方法是启动另一个线程并在后台进行搜索,并让后台线程检查取消标志以防用户想要停止操作,因此它可以发布有关多少时间的信息左,完成百分比等,等等。它有点粗糙,但这应该让任何对这种类型的事情感兴趣的人朝着正确的方向前进。并记住始终正确检查错误并进行异常处理,这是我看到新程序员一直跳过的事情。

回答by Bodislav Nicolae

Try this on Linux:

在 Linux 上试试这个:

#include <iostream>
#include <string>
#include <dirent.h>

void ProcessDirectory(std::string directory);
void ProcessFile(std::string file);
void ProcessEntity(struct dirent* entity);

std::string path = "/path/to/directory/";

int main()
{
    std::string directory = "theDirectoryYouWant";
    ProcessDirectory(directory);    

    return 0;
}

void ProcessDirectory(std::string directory)
{
    std::string dirToOpen = path + directory;
    auto dir = opendir(dirToOpen.c_str());

    //set the new path for the content of the directory
    path = dirToOpen + "/";

    std::cout << "Process directory: " << dirToOpen.c_str() << std::endl;

    if(NULL == dir)
    {
        std::cout << "could not open directory: " << dirToOpen.c_str() << std::endl;
        return;
    }

    auto entity = readdir(dir);

    while(entity != NULL)
    {
        ProcessEntity(entity);
        entity = readdir(dir);
    }

    //we finished with the directory so remove it from the path
    path.resize(path.length() - 1 - directory.length());
    closedir(dir);
}

void ProcessEntity(struct dirent* entity)
{
    //find entity type
    if(entity->d_type == DT_DIR)
    {//it's an direcotry
        //don't process the  '..' and the '.' directories
        if(entity->d_name[0] == '.')
        {
            return;
        }

        //it's an directory so process it
        ProcessDirectory(std::string(entity->d_name));
        return;
    }

    if(entity->d_type == DT_REG)
    {//regular file
        ProcessFile(std::string(entity->d_name));
        return;
    }

    //there are some other types
    //read here http://linux.die.net/man/3/readdir
    std::cout << "Not a file or directory: " << entity->d_name << std::endl;
}

void ProcessFile(std::string file)
{
    std::cout << "Process file     : " << fileToOpen.c_str() << std::endl;

    //if you want to do something with the file add your code here
}

回答by Jorge Israel Pe?a

Use nftw. It provides various options to fine-tune the directory traversal.

使用nftw. 它提供了各种选项来微调目录遍历。

That page also shows an example.

该页面还显示了一个示例

回答by Dietrich Epp

Recursion is unnecessary. There is a facility on Linux to do this iteratively.

递归是不必要的。Linux 上有一个工具可以迭代地执行此操作。

#include <ftw.h>

int ftw(const char *dirpath,
        int (*fn) (const char *fpath, const struct stat *sb,
                   int typeflag),
        int nopenfd);

The ftw()function calls the supplied callback for every file and directory in the given tree.

ftw()函数为给定树中的每个文件和目录调用提供的回调。