¿Cómo obtener todos los archivos bajo un directorio específico en MATLAB?


Necesito obtener todos esos archivos bajo D:\dic y hacer un bucle sobre ellos para procesarlos individualmente.

¿MATLAB soporta este tipo de operaciones?

Se puede hacer en otros scripts como PHP,Python...

Author: gnovice, 2010-04-16

8 answers

Update: Dado que este post es bastante antiguo, y he modificado esta utilidad mucho para mi propio uso durante ese tiempo, pensé que debería publicar una nueva versión. Mi código más reciente se puede encontrar en El Intercambio de archivos de MathWorks: dirPlus.m. También puedes obtener la fuente desde GitHub .

Hice una serie de mejoras. Ahora le da opciones para anteponer la ruta completa o devolver solo el nombre del archivo (incorporado desde Doresoom y Oz Radiano ) y aplicar un patrón de expresión regular a los nombres de archivo (incorporado desde Peter D). Además, agregué la capacidad de aplicar una función de validación a cada archivo, lo que le permite seleccionarlos en función de criterios que no sean solo sus nombres (es decir, tamaño del archivo, contenido, fecha de creación, etc.).).


NOTA: En las versiones más recientes de MATLAB (R2016b y posteriores), el dir función tiene capacidades de búsqueda recursiva! Así que usted puede hacer esto para obtener una lista de todos los archivos *.m en todas las subcarpetas de la carpeta actual:

dirData = dir('**/*.m');

Código antiguo: (para la posteridad)

Aquí hay una función que busca recursivamente a través de todos los subdirectorios de un directorio dado, recopilando una lista de todos los nombres de archivo que encuentra:

function fileList = getAllFiles(dirName)

  dirData = dir(dirName);      %# Get the data for the current directory
  dirIndex = [dirData.isdir];  %# Find the index for directories
  fileList = {dirData(~dirIndex).name}';  %'# Get a list of the files
  if ~isempty(fileList)
    fileList = cellfun(@(x) fullfile(dirName,x),...  %# Prepend path to files
                       fileList,'UniformOutput',false);
  end
  subDirs = {dirData(dirIndex).name};  %# Get a list of the subdirectories
  validIndex = ~ismember(subDirs,{'.','..'});  %# Find index of subdirectories
                                               %#   that are not '.' or '..'
  for iDir = find(validIndex)                  %# Loop over valid subdirectories
    nextDir = fullfile(dirName,subDirs{iDir});    %# Get the subdirectory path
    fileList = [fileList; getAllFiles(nextDir)];  %# Recursively call getAllFiles
  end

end

Después de guardar la función anterior en algún lugar de su ruta de MATLAB, puede llamarla de la siguiente manera:

fileList = getAllFiles('D:\dic');
 125
Author: gnovice,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 10:31:16

Está buscando dir para devolver el contenido del directorio.

Para recorrer los resultados, simplemente puede hacer lo siguiente:

dirlist = dir('.');
for i = 1:length(dirlist)
    dirlist(i)
end

Esto debería darle la salida en el siguiente formato, por ejemplo:

name: 'my_file'
date: '01-Jan-2010 12:00:00'
bytes: 56
isdir: 0
datenum: []
 23
Author: James B,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-01-10 13:30:30

Usé el código mencionado en esta gran respuesta y lo expandí para soportar 2 parámetros adicionales que necesitaba en mi caso. Los parámetros son extensiones de archivo para filtrar y un indicador que indica si concatenar la ruta completa al nombre del archivo o no.

Espero que sea lo suficientemente claro y que alguien lo encuentre beneficioso.

function fileList = getAllFiles(dirName, fileExtension, appendFullPath)

  dirData = dir([dirName '/' fileExtension]);      %# Get the data for the current directory
  dirWithSubFolders = dir(dirName);
  dirIndex = [dirWithSubFolders.isdir];  %# Find the index for directories
  fileList = {dirData.name}';  %'# Get a list of the files
  if ~isempty(fileList)
    if appendFullPath
      fileList = cellfun(@(x) fullfile(dirName,x),...  %# Prepend path to files
                       fileList,'UniformOutput',false);
    end
  end
  subDirs = {dirWithSubFolders(dirIndex).name};  %# Get a list of the subdirectories
  validIndex = ~ismember(subDirs,{'.','..'});  %# Find index of subdirectories
                                               %#   that are not '.' or '..'
  for iDir = find(validIndex)                  %# Loop over valid subdirectories
    nextDir = fullfile(dirName,subDirs{iDir});    %# Get the subdirectory path
    fileList = [fileList; getAllFiles(nextDir, fileExtension, appendFullPath)];  %# Recursively call getAllFiles
  end

end

Ejemplo para ejecutar el código:

fileList = getAllFiles(dirName, '*.xml', 0); %#0 is false obviously
 13
Author: Oz Radiano,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 12:10:08

Puede usar regexp o strcmp para eliminar . y .. O puede usar el campo isdir si solo desea archivos en el directorio, no carpetas.

list=dir(pwd);  %get info of files/folders in current directory
isfile=~[list.isdir]; %determine index of files vs folders
filenames={list(isfile).name}; %create cell array of file names

O combinar las dos últimas líneas:

filenames={list(~[list.isdir]).name};

Para una lista de carpetas en el directorio excluyendo. y ..

dirnames={list([list.isdir]).name};
dirnames=dirnames(~(strcmp('.',dirnames)|strcmp('..',dirnames)));

Desde este punto, debería ser capaz de lanzar el código en un bucle for anidado, y continuar buscando en cada subcarpeta hasta que sus dirnames devuelvan una celda vacía para cada subdirectorio.

 8
Author: Doresoom,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-04-16 15:20:33

Esta respuesta no responde directamente a la pregunta, pero puede ser una buena solución fuera de la caja.

Voté a favor de la solución de gnovice, pero quiero ofrecer otra solución: Use el comando dependiente del sistema de su sistema operativo:

tic
asdfList = getAllFiles('../TIMIT_FULL/train');
toc
% Elapsed time is 19.066170 seconds.

tic
[status,cmdout] = system('find ../TIMIT_FULL/train/ -iname "*.wav"');
C = strsplit(strtrim(cmdout));
toc
% Elapsed time is 0.603163 seconds.

Positivo:

  • Muy rápido (en mi caso para una base de datos de 18000 archivos en linux).
  • Puede utilizar soluciones bien probadas.
  • No es necesario aprender o reinventar una nueva sintaxis para seleccionar, es decir, *.wav file.

Negativo:

  • Usted no es independiente del sistema.
  • Usted confía en una sola cadena que puede ser difícil de analizar.
 7
Author: Lukas,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-04-02 08:31:55

No conozco un método de función única para esto, pero puede usar genpath para recurrir a una lista de subdirectorios solo. Esta lista se devuelve como una cadena de directorios delimitada por punto y coma, por lo que tendrá que separarla usando strread, es decir,

dirlist = strread(genpath('/path/of/directory'),'%s','delimiter',';')

Si no desea incluir el directorio dado, elimine la primera entrada de dirlist, es decir, dirlist(1)=[]; ya que siempre es la primera entrada.

A continuación, obtener la lista de archivos en cada directorio con un bucle dir.

filenamelist=[];
for d=1:length(dirlist)
    % keep only filenames
    filelist=dir(dirlist{d});
    filelist={filelist.name};

    % remove '.' and '..' entries
    filelist([strmatch('.',filelist,'exact');strmatch('..',filelist,'exact'))=[];
    % or to ignore all hidden files, use filelist(strmatch('.',filelist))=[];

    % prepend directory name to each filename entry, separated by filesep*
    for f=1:length(filelist)
        filelist{f}=[dirlist{d} filesep filelist{f}];
    end

    filenamelist=[filenamelist filelist];
end

filesep devuelve el separador de directorios de la plataforma en la que se ejecuta MATLAB.

Esto le da una lista de nombres de archivo con rutas completas en la matriz de celdas filenamelist. No es la mejor solución, lo sé.

 3
Author: JS Ng,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-04-16 15:22:20

Esta es una función útil para obtener nombres de archivo, con el formato especificado (generalmente .mat) en una carpeta raíz!

    function filenames = getFilenames(rootDir, format)
        % Get filenames with specified `format` in given `foler` 
        %
        % Parameters
        % ----------
        % - rootDir: char vector
        %   Target folder
        % - format: char vector = 'mat'
        %   File foramt

        % default values
        if ~exist('format', 'var')
            format = 'mat';
        end

        format = ['*.', format];
        filenames = dir(fullfile(rootDir, format));
        filenames = arrayfun(...
            @(x) fullfile(x.folder, x.name), ...
            filenames, ...
            'UniformOutput', false ...
        );
    end

En su caso, puede usar el siguiente fragmento :)

filenames = getFilenames('D:/dic/**');
for i = 1:numel(filenames)
    filename = filenames{i};
    % do your job!
end
 1
Author: Yas,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-09-10 11:03:14

Con pocas modificaciones pero un enfoque casi similar para obtener la ruta completa del archivo de cada subcarpeta

dataFolderPath = 'UCR_TS_Archive_2015/';

dirData = dir(dataFolderPath);      %# Get the data for the current directory
dirIndex = [dirData.isdir];  %# Find the index for directories
fileList = {dirData(~dirIndex).name}';  %'# Get a list of the files
if ~isempty(fileList)
    fileList = cellfun(@(x) fullfile(dataFolderPath,x),...  %# Prepend path to files
        fileList,'UniformOutput',false);
end
subDirs = {dirData(dirIndex).name};  %# Get a list of the subdirectories
validIndex = ~ismember(subDirs,{'.','..'});  %# Find index of subdirectories
%#   that are not '.' or '..'
for iDir = find(validIndex)                  %# Loop over valid subdirectories
    nextDir = fullfile(dataFolderPath,subDirs{iDir});    %# Get the subdirectory path
    getAllFiles = dir(nextDir);
    for k = 1:1:size(getAllFiles,1)
        validFileIndex = ~ismember(getAllFiles(k,1).name,{'.','..'});
        if(validFileIndex)
            filePathComplete = fullfile(nextDir,getAllFiles(k,1).name);
            fprintf('The Complete File Path: %s\n', filePathComplete);
        end
    end
end  
 0
Author: Spandan,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-01-02 12:02:17