¿Cómo puedo determinar la lista de archivos en un directorio desde mi código C o C ++?
No tengo permiso para ejecutar el ls
comando y analizar los resultados desde mi programa.
¿Cómo puedo determinar la lista de archivos en un directorio desde mi código C o C ++?
No tengo permiso para ejecutar el ls
comando y analizar los resultados desde mi programa.
Respuestas:
En tareas pequeñas y simples, no uso boost, uso dirent.h, que también está disponible para 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;
}
Es solo un pequeño archivo de encabezado y hace la mayoría de las cosas simples que necesita sin usar un gran enfoque basado en plantillas como boost (sin ofender, ¡me gusta boost!).
El autor de la capa de compatibilidad de Windows es Toni Ronkko. En Unix, es un encabezado estándar.
ACTUALIZACIÓN 2017 :
En C ++ 17 ahora hay una forma oficial de archivos de lista de su sistema de archivos: std::filesystem
. Hay una excelente respuesta de Shreevardhan a continuación con este código fuente:
#include <string>
#include <iostream>
#include <filesystem>
namespace 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;
}
std::experimental::filesystem
, con C ++ 17 existe std::filesystem
. Ver la respuesta de Shreevardhan a continuación. Por lo tanto, no necesita bibliotecas de terceros.
C ++ 17 ahora tiene un std::filesystem::directory_iterator
, que se puede usar como
#include <string>
#include <iostream>
#include <filesystem>
namespace 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;
}
Además, también std::filesystem::recursive_directory_iterator
puede iterar los subdirectorios.
namespace fs = std::experimental::filesystem;
. Aunque parece funcionar bien.
std::filesystem::path
a std::cout
, las comillas se incluyen en la salida. Para evitar eso, agregue .string()
a la ruta para hacer una conversión explícita en lugar de implícita (aquí std::cout << p.string() << std::endl;
). Ejemplo: coliru.stacked-crooked.com/view?id=a55ea60bbd36a8a3
std::wstring
debería usarse o cuál es el tipo del iterador?
-lstdc++fs
, obtendría un SIGSEGV (Address boundary error)
. No pude encontrar en ninguna parte de la documentación que esto fuera necesario, y el enlazador tampoco dio ninguna pista. Esto funcionó para ambos g++ 8.3.0
y clang 8.0.0-3
. ¿Alguien tiene alguna idea de dónde se especifica este tipo de cosas en los documentos / especificaciones?
Desafortunadamente, el estándar C ++ no define una forma estándar de trabajar con archivos y carpetas de esta manera.
Dado que no existe una forma multiplataforma, la mejor forma multiplataforma es utilizar una biblioteca como el módulo de sistema de archivos boost .
Método de impulso multiplataforma:
La siguiente función, dada una ruta de directorio y un nombre de archivo, busca de forma recursiva el nombre del archivo en el directorio y sus subdirectorios, devuelve un bool y, si tiene éxito, la ruta al archivo que se encontró.
bool find_file(const path & dir_path, // in this directory, const std::string & file_name, // search for this name, path & path_found) // placing path here if found { if (!exists(dir_path)) return false; directory_iterator end_itr; // default construction yields past-the-end for (directory_iterator itr(dir_path); itr != end_itr; ++itr) { if (is_directory(itr->status())) { if (find_file(itr->path(), file_name, path_found)) return true; } else if (itr->leaf() == file_name) // see below { path_found = itr->path(); return true; } } return false; }
Fuente de la página de impulso mencionada anteriormente.
Para sistemas basados en Unix / Linux:
Puede usar opendir / readdir / closedir .
El código de muestra que busca en un directorio la entrada `` nombre '' es:
len = strlen(name); dirp = opendir("."); while ((dp = readdir(dirp)) != NULL) if (dp->d_namlen == len && !strcmp(dp->d_name, name)) { (void)closedir(dirp); return FOUND; } (void)closedir(dirp); return NOT_FOUND;
Código fuente de las páginas de manual anteriores.
Para sistemas basados en Windows:
Puede utilizar las API de Win32 FindFirstFile / FindNextFile / FindClose funciones.
El siguiente ejemplo de C ++ muestra un uso mínimo de FindFirstFile.
#include <windows.h> #include <tchar.h> #include <stdio.h> void _tmain(int argc, TCHAR *argv[]) { WIN32_FIND_DATA FindFileData; HANDLE hFind; if( argc != 2 ) { _tprintf(TEXT("Usage: %s [target_file]\n"), argv[0]); return; } _tprintf (TEXT("Target file is %s\n"), argv[1]); hFind = FindFirstFile(argv[1], &FindFileData); if (hFind == INVALID_HANDLE_VALUE) { printf ("FindFirstFile failed (%d)\n", GetLastError()); return; } else { _tprintf (TEXT("The first file found is %s\n"), FindFileData.cFileName); FindClose(hFind); } }
Código fuente de las páginas msdn anteriores.
FindFirstFile(TEXT("D:\\IMAGE\\MYDIRECTORY\\*"), &findFileData);
std::experimental::filesystem
, con C ++ 17 existe std::filesystem
, que tiene una funcionalidad similar a boost (las libs se derivan de boost). Ver la respuesta de Shreevardhan a continuación.
Una función es suficiente, no necesita usar ninguna biblioteca de terceros (para Windows).
#include <Windows.h>
vector<string> get_all_files_names_within_folder(string folder)
{
vector<string> names;
string search_path = folder + "/*.*";
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) ) {
names.push_back(fd.cFileName);
}
}while(::FindNextFile(hFind, &fd));
::FindClose(hFind);
}
return names;
}
PD: como mencionó @Sebastian, puede cambiar *.*
a *.ext
para obtener solo los archivos EXT (es decir, de un tipo específico) en ese directorio.
std::vector<std::wstring>
y luego en fileName.c_str()
lugar de un vector de cadenas, que no se compilaría.
Para una solución única en C, por favor revise esto. Solo requiere un encabezado adicional:
https://github.com/cxong/tinydir
tinydir_dir dir;
tinydir_open(&dir, "/path/to/dir");
while (dir.has_next)
{
tinydir_file file;
tinydir_readfile(&dir, &file);
printf("%s", file.name);
if (file.is_dir)
{
printf("/");
}
printf("\n");
tinydir_next(&dir);
}
tinydir_close(&dir);
Algunas ventajas sobre otras opciones:
readdir_r
donde esté disponible, lo que significa que (generalmente) es seguro para subprocesosUNICODE
macrosRecomiendo usar glob
con este envoltorio reutilizable. Genera una ruta vector<string>
correspondiente al archivo que se ajusta al patrón global:
#include <glob.h>
#include <vector>
using std::vector;
vector<string> globVector(const string& pattern){
glob_t glob_result;
glob(pattern.c_str(),GLOB_TILDE,NULL,&glob_result);
vector<string> files;
for(unsigned int i=0;i<glob_result.gl_pathc;++i){
files.push_back(string(glob_result.gl_pathv[i]));
}
globfree(&glob_result);
return files;
}
Que luego se puede llamar con un patrón comodín del sistema normal como:
vector<string> files = globVector("./*");
No such file or directory
. ¿Me puede decir cómo resolver este problema, por favor?
GLOB_TILDE
con GLOB_TILDE | GLOB_MARK
y luego la comprobación de caminos que terminan en una barra. Tendrá que hacer cualquier modificación si lo necesita.
glob
.
Aquí hay un código muy simple al C++11
usar la boost::filesystem
biblioteca para obtener nombres de archivos en un directorio (excluyendo los nombres de carpetas):
#include <string>
#include <iostream>
#include <boost/filesystem.hpp>
using namespace std;
using namespace boost::filesystem;
int main()
{
path p("D:/AnyFolder");
for (auto i = directory_iterator(p); i != directory_iterator(); i++)
{
if (!is_directory(i->path())) //we eliminate directories
{
cout << i->path().filename().string() << endl;
}
else
continue;
}
}
La salida es como:
file1.txt
file2.dat
boost::filesystem
biblioteca boost.org/doc/libs/1_58_0/libs/filesystem/doc/index.htm
¿Por qué no usar 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;
}
Creo que el siguiente fragmento se puede usar para enumerar todos los archivos.
#include <stdio.h>
#include <dirent.h>
#include <sys/types.h>
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);
}
A continuación se muestra la estructura de la estructura dirent.
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 */
};
Prueba el método boost para x-platform
http://www.boost.org/doc/libs/1_38_0/libs/filesystem/doc/index.htm
o simplemente use su archivo de sistema operativo específico.
Echa un vistazo a esta clase que usa la API win32. Simplemente construya una instancia proporcionando el nombre foldername
del cual desea el listado y luego llame al getNextFile
método para obtener el siguiente filename
del directorio. Creo que necesita windows.h
y stdio.h
.
class FileGetter{
WIN32_FIND_DATAA found;
HANDLE hfind;
char folderstar[255];
int chk;
public:
FileGetter(char* folder){
sprintf(folderstar,"%s\\*.*",folder);
hfind = FindFirstFileA(folderstar,&found);
//skip .
FindNextFileA(hfind,&found);
}
int getNextFile(char* fname){
//skips .. when called for the first time
chk=FindNextFileA(hfind,&found);
if (chk)
strcpy(fname, found.cFileName);
return chk;
}
};
GNU Manual FTW
Además, a veces es bueno ir directamente a la fuente (juego de palabras). Puedes aprender mucho mirando las entrañas de algunos de los comandos más comunes en Linux. He configurado un espejo simple de los coreutils de GNU en github (para leer).
https://github.com/homer6/gnu_coreutils/blob/master/src/ls.c
Tal vez esto no aborde Windows, pero se pueden tener varios casos de uso de variantes de Unix utilizando estos métodos.
Espero que ayude...
La respuesta de Shreevardhan funciona muy bien. Pero si quieres usarlo en c ++ 14 solo haz un cambionamespace fs = experimental::filesystem;
es decir,
#include <string>
#include <iostream>
#include <filesystem>
using namespace std;
namespace fs = experimental::filesystem;
int main()
{
string path = "C:\\splits\\";
for (auto & p : fs::directory_iterator(path))
cout << p << endl;
int n;
cin >> n;
}
char **getKeys(char *data_dir, char* tablename, int *num_keys)
{
char** arr = malloc(MAX_RECORDS_PER_TABLE*sizeof(char*));
int i = 0;
for (;i < MAX_RECORDS_PER_TABLE; i++)
arr[i] = malloc( (MAX_KEY_LEN+1) * sizeof(char) );
char *buf = (char *)malloc( (MAX_KEY_LEN+1)*sizeof(char) );
snprintf(buf, MAX_KEY_LEN+1, "%s/%s", data_dir, tablename);
DIR* tableDir = opendir(buf);
struct dirent* getInfo;
readdir(tableDir); // ignore '.'
readdir(tableDir); // ignore '..'
i = 0;
while(1)
{
getInfo = readdir(tableDir);
if (getInfo == 0)
break;
strcpy(arr[i++], getInfo->d_name);
}
*(num_keys) = i;
return arr;
}
Espero que este código te ayude.
#include <windows.h>
#include <iostream>
#include <string>
#include <vector>
using namespace std;
string wchar_t2string(const wchar_t *wchar)
{
string str = "";
int index = 0;
while(wchar[index] != 0)
{
str += (char)wchar[index];
++index;
}
return str;
}
wchar_t *string2wchar_t(const string &str)
{
wchar_t wchar[260];
int index = 0;
while(index < str.size())
{
wchar[index] = (wchar_t)str[index];
++index;
}
wchar[index] = 0;
return wchar;
}
vector<string> listFilesInDirectory(string directoryName)
{
WIN32_FIND_DATA FindFileData;
wchar_t * FileName = string2wchar_t(directoryName);
HANDLE hFind = FindFirstFile(FileName, &FindFileData);
vector<string> listFileNames;
listFileNames.push_back(wchar_t2string(FindFileData.cFileName));
while (FindNextFile(hFind, &FindFileData))
listFileNames.push_back(wchar_t2string(FindFileData.cFileName));
return listFileNames;
}
void main()
{
vector<string> listFiles;
listFiles = listFilesInDirectory("C:\\*.txt");
for each (string str in listFiles)
cout << str << endl;
}
string2wchar_t
devuelve la dirección de una variable local. Además, probablemente debería usar los métodos de conversión disponibles en WinAPI en lugar de escribir los suyos propios.
Esta implementación cumple su propósito, llenando dinámicamente una serie de cadenas con el contenido del directorio especificado.
int exploreDirectory(const char *dirpath, char ***list, int *numItems) {
struct dirent **direntList;
int i;
errno = 0;
if ((*numItems = scandir(dirpath, &direntList, NULL, alphasort)) == -1)
return errno;
if (!((*list) = malloc(sizeof(char *) * (*numItems)))) {
fprintf(stderr, "Error in list allocation for file list: dirpath=%s.\n", dirpath);
exit(EXIT_FAILURE);
}
for (i = 0; i < *numItems; i++) {
(*list)[i] = stringDuplication(direntList[i]->d_name);
}
for (i = 0; i < *numItems; i++) {
free(direntList[i]);
}
free(direntList);
return 0;
}
if
bloque. Lo llamo conchar **list; int numItems; exploreDirectory("/folder",list, numItems);
Esto funciona para mi. Lo siento si no puedo recordar la fuente. Probablemente sea de una página de manual.
#include <ftw.h>
int AnalizeDirectoryElement (const char *fpath,
const struct stat *sb,
int tflag,
struct FTW *ftwbuf) {
if (tflag == FTW_F) {
std::string strFileName(fpath);
DoSomethingWith(strFileName);
}
return 0;
}
void WalkDirectoryTree (const char * pchFileName) {
int nFlags = 0;
if (nftw(pchFileName, AnalizeDirectoryElement, 20, nFlags) == -1) {
perror("nftw");
}
}
int main() {
WalkDirectoryTree("some_dir/");
}
puede obtener todos los archivos directos en su directorio raíz utilizando std :: experimental :: filesystem :: directory_iterator (). Luego, lea el nombre de estos archivos de ruta.
#include <iostream>
#include <filesystem>
#include <string>
#include <direct.h>
using namespace std;
namespace fs = std::experimental::filesystem;
void ShowListFile(string path)
{
for(auto &p: fs::directory_iterator(path)) /*get directory */
cout<<p.path().filename()<<endl; // get file name
}
int main() {
ShowListFile("C:/Users/dell/Pictures/Camera Roll/");
getchar();
return 0;
}
Esta respuesta debería funcionar para los usuarios de Windows que han tenido problemas para que esto funcione con Visual Studio con cualquiera de las otras respuestas.
Descargue el archivo dirent.h de la página de github. Pero es mejor usar el archivo Raw dirent.h y seguir mis pasos a continuación (así es como lo hice funcionar).
Página de Github para dirent.h para Windows: página de Github para dirent.h
Archivo Dirent sin procesar: Archivo dirent.h sin procesar
Vaya a su proyecto y agregue un nuevo elemento ( Ctrl+ Shift+ A). Agregue un archivo de encabezado (.h) y asígnele el nombre dirent.h.
Pegue el código del archivo Raw dirent.h en su encabezado.
Incluya "dirent.h" en su código.
Ponga el siguiente void filefinder()
método en su código y llámelo desde su main
función o edite la función como quiera usarlo.
#include <stdio.h>
#include <string.h>
#include "dirent.h"
string path = "C:/folder"; //Put a valid path here for folder
void filefinder()
{
DIR *directory = opendir(path.c_str());
struct dirent *direntStruct;
if (directory != NULL) {
while (direntStruct = readdir(directory)) {
printf("File Name: %s\n", direntStruct->d_name); //If you are using <stdio.h>
//std::cout << direntStruct->d_name << std::endl; //If you are using <iostream>
}
}
closedir(directory);
}
El sistema lo llama!
system( "dir /b /s /a-d * > file_names.txt" );
Entonces solo lee el archivo.
EDITAR: esta respuesta debe considerarse un truco, pero realmente funciona (aunque sea de forma específica para la plataforma) si no tiene acceso a soluciones más elegantes.
Dado que los archivos y subdirectorios de un directorio generalmente se almacenan en una estructura de árbol, una forma intuitiva es usar el algoritmo DFS para recorrer recursivamente cada uno de ellos. Aquí hay un ejemplo en el sistema operativo Windows utilizando funciones básicas de archivo en io.h. Puede reemplazar estas funciones en otra plataforma. Lo que quiero expresar es que la idea básica de DFS cumple perfectamente con este problema.
#include<io.h>
#include<iostream.h>
#include<string>
using namespace std;
void TraverseFilesUsingDFS(const string& folder_path){
_finddata_t file_info;
string any_file_pattern = folder_path + "\\*";
intptr_t handle = _findfirst(any_file_pattern.c_str(),&file_info);
//If folder_path exsist, using any_file_pattern will find at least two files "." and "..",
//of which "." means current dir and ".." means parent dir
if (handle == -1){
cerr << "folder path not exist: " << folder_path << endl;
exit(-1);
}
//iteratively check each file or sub_directory in current folder
do{
string file_name=file_info.name; //from char array to string
//check whtether it is a sub direcotry or a file
if (file_info.attrib & _A_SUBDIR){
if (file_name != "." && file_name != ".."){
string sub_folder_path = folder_path + "\\" + file_name;
TraverseFilesUsingDFS(sub_folder_path);
cout << "a sub_folder path: " << sub_folder_path << endl;
}
}
else
cout << "file name: " << file_name << endl;
} while (_findnext(handle, &file_info) == 0);
//
_findclose(handle);
}
Traté de seguir el ejemplo dado en ambas respuestas y podría valer la pena señalar que parece que std::filesystem::directory_entry
se ha cambiado para no tener una sobrecarga del <<
operador. En lugar de std::cout << p << std::endl;
tener que usar lo siguiente para poder compilar y hacer que funcione:
#include <iostream>
#include <filesystem>
#include <string>
namespace fs = std::filesystem;
int main() {
std::string path = "/path/to/directory";
for(const auto& p : fs::directory_iterator(path))
std::cout << p.path() << std::endl;
}
tratando de pasar p
por sí solo para dar como std::cout <<
resultado un error de sobrecarga faltante.
Sobre la base de lo que herohuyongtao publicó y algunas otras publicaciones:
http://www.cplusplus.com/forum/general/39766/
¿Cuál es el tipo de entrada esperado de FindFirstFile?
¿Cómo convertir wstring en cadena?
Esta es una solución de Windows.
Como quería pasar std :: string y devolver un vector de cadenas, tuve que hacer un par de conversiones.
#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;
}
WIN32_FIND_DATAA
, FindFirstFileA
y FindNextFileA
. Entonces no habrá necesidad de convertir el resultado a multibyte o la entrada a unicode.
Es algo que quiero compartir y gracias por el material de lectura. Juega un poco con la función para entenderla. Te puede gustar. e representaba la extensión, p es para la ruta y s es para el separador de ruta.
Si la ruta se pasa sin terminar el separador, se agregará un separador a la ruta. Para la extensión, si se ingresa una cadena vacía, la función devolverá cualquier archivo que no tenga una extensión en su nombre. Si se ingresó una sola estrella, se devolverán todos los archivos del directorio. Si la longitud de e es mayor que 0 pero no es un solo *, entonces un punto se antepondrá a e si e no hubiera contenido un punto en la posición cero.
Por un valor de retorno. Si se devuelve un mapa de longitud cero, entonces no se encontró nada, pero el directorio estaba abierto. Si el índice 999 está disponible desde el valor de retorno pero el tamaño del mapa es solo 1, eso significa que hubo un problema al abrir la ruta del directorio.
Tenga en cuenta que, para mayor eficiencia, esta función se puede dividir en 3 funciones más pequeñas. Además de eso, puede crear una función de llamada que detectará a qué función va a llamar en función de la entrada. ¿Por qué es eso más eficiente? Dijo que si va a capturar todo lo que es un archivo, al hacer ese método, la subfunción que se creó para capturar todos los archivos simplemente capturará todos los archivos y no necesita evaluar ninguna otra condición innecesaria cada vez que encuentra un archivo.
Eso también se aplicaría cuando tomas archivos que no tienen una extensión. Una función construida específica para ese propósito solo evaluaría el clima si el objeto encontrado es un archivo y luego si el nombre del archivo tiene un punto o no.
El ahorro puede no ser mucho si solo lee directorios con no tantos archivos. Pero si está leyendo una cantidad masiva de directorio o si el directorio tiene un par de cientos de miles de archivos, podría ser un gran ahorro.
#include <stdio.h>
#include <sys/stat.h>
#include <iostream>
#include <dirent.h>
#include <map>
std::map<int, std::string> getFile(std::string p, std::string e = "", unsigned char s = '/'){
if ( p.size() > 0 ){
if (p.back() != s) p += s;
}
if ( e.size() > 0 ){
if ( e.at(0) != '.' && !(e.size() == 1 && e.at(0) == '*') ) e = "." + e;
}
DIR *dir;
struct dirent *ent;
struct stat sb;
std::map<int, std::string> r = {{999, "FAILED"}};
std::string temp;
int f = 0;
bool fd;
if ( (dir = opendir(p.c_str())) != NULL ){
r.erase (999);
while ((ent = readdir (dir)) != NULL){
temp = ent->d_name;
fd = temp.find(".") != std::string::npos? true : false;
temp = p + temp;
if (stat(temp.c_str(), &sb) == 0 && S_ISREG(sb.st_mode)){
if ( e.size() == 1 && e.at(0) == '*' ){
r[f] = temp;
f++;
} else {
if (e.size() == 0){
if ( fd == false ){
r[f] = temp;
f++;
}
continue;
}
if (e.size() > temp.size()) continue;
if ( temp.substr(temp.size() - e.size()) == e ){
r[f] = temp;
f++;
}
}
}
}
closedir(dir);
return r;
} else {
return r;
}
}
void printMap(auto &m){
for (const auto &p : m) {
std::cout << "m[" << p.first << "] = " << p.second << std::endl;
}
}
int main(){
std::map<int, std::string> k = getFile("./", "");
printMap(k);
return 0;
}
#include<iostream>
#include <dirent.h>
using namespace std;
char ROOT[]={'.'};
void listfiles(char* path){
DIR * dirp = opendir(path);
dirent * dp;
while ( (dp = readdir(dirp)) !=NULL ) {
cout << dp->d_name << " size " << dp->d_reclen<<std::endl;
}
(void)closedir(dirp);
}
int main(int argc, char **argv)
{
char* path;
if (argc>1) path=argv[1]; else path=ROOT;
cout<<"list files in ["<<path<<"]"<<std::endl;
listfiles(path);
return 0;
}
Esto funcionó para mí. Escribe un archivo con solo los nombres (sin ruta) de todos los archivos. Luego lee ese archivo txt y lo imprime por usted.
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;
}
}