regulares expresiones regex linux bash find ls

regex - expresiones - Encuentra el número de archivos que coinciden con un patrón en un directorio en Linux



sed expresiones regulares (5)

Soy nuevo en Linux. Tengo un directorio en Linux con aproximadamente 250,000 archivos que necesito para encontrar el número de archivos que coinciden con un patrón.

Intenté usar el siguiente comando:

ls -1 20061101-20131101_kh5x7tte9n_2010_* | wc -l

Recibí el siguiente mensaje de error:

-bash: /bin/ls: Argument list too long 0

Por favor ayuda. Gracias por adelantado


Podría ser mejor usar find para esto:

find . -name "pattern_*" -printf ''.'' | wc -l

En su caso específico:

find . -maxdepth 1 -name "20061101-20131101_kh5x7tte9n_2010_*" -printf ''.'' | wc -l

find devolverá una lista de archivos que coinciden con los criterios. -maxdepth 1 hará que la búsqueda se realice solo en la ruta, sin subdirectorios ( gracias Petesh! ). -printf ''.'' imprimirá un punto para cada coincidencia, de modo que los nombres con nuevas líneas no harán que wc -l rompa.

Entonces wc -l indicará el número de líneas.

Comparación de rendimiento de dos opciones posibles:

Vamos a crear 10 000 archivos con este patrón:

$ for i in {1..10000}; do touch 20061101-20131101_kh5x7tte9n_201_$i; done

Y luego compare el tiempo que lleva obtener el resultado con ls -1 ... o find ... :

$ time find . -maxdepth 1 -name "20061101-20131101_kh5x7tte9n_201_*" | wc -l 10000 real 0m0.034s user 0m0.017s sys 0m0.021s $ time ls -1 | grep 20061101-20131101_kh5x7tte9n_201 | wc -l 10000 real 0m0.254s user 0m0.245s sys 0m0.020s

find es x5 veces más rápido! Pero si usamos ls -1fgracias Petesh otra vez! ), Entonces ls es incluso más rápido que find :

$ time ls -1f | grep 20061101-20131101_kh5x7tte9n_201 | wc -l 10000 real 0m0.023s user 0m0.020s sys 0m0.012s


Por lo general, debe evitar ls en los scripts y, de hecho, realizar el cálculo en una función de shell evitará el error de "lista de argumentos demasiado larga" porque no hay un límite exec y por lo tanto el límite ARGV_MAX no entra en juego.

number_of_files () { if [ -e "$1" ]; then echo "$#" else echo 0 fi }

Las protecciones condicionales contra el globo no se expanden en absoluto (que es la shopt -s nullglob predeterminada fuera de la caja; en Bash, puede shopt -s nullglob para hacer comodines que no coincidan con ningún archivo expandido en la cadena vacía).

Intentalo:

number_of_files 20061101-20131101_kh5x7tte9n_2010_*


Prueba esto:

ls -1 | grep 20061101-20131101_kh5x7tte9n_2010_ | wc -l


tienes un "argumento demasiado largo" porque el shell expande tu patrón a la lista de archivos. tratar:

find -maxdepth 1 -name ''20061101-20131101_kh5x7tte9n_2010_*'' |wc -l

preste atención: el patrón se incluye entre comillas para evitar la expansión de la carcasa


ls -1 | grep ''20061101-20131101_kh5x7tte9n_2010_*'' | wc -l

La respuesta anterior no incluía citas sobre criterios de búsqueda ni * comodín.