la acción de búsqueda no funciona para una búsqueda específica

la acción de búsqueda no funciona para una búsqueda específica

Estoy intentando utilizar el findcomando para enumerar el tamaño de un determinado conjunto de archivos, pero no obtengo ningún resultado. El comando que uso es:

find POD -type f -name *.mp3 -or -name *.ogg -ls

Lo que no produce ningún resultado. Mientras:

find POD -type f -name *.mp3 -or -name *.ogg

produce resultados, también probé las acciones:

-printf "%p %k KB\n"
-exec ls -ls '{}' \;
-print0

pero todos estos no dan resultados. Cuando uso cualquiera de estas acciones con una expresión diferente, por ejemplo:

find . -maxdepth 1 -type f -printf "%p %k KB\n"

También obtengo el resultado esperado. ¿Alguien tiene alguna idea de cuál es el problema? Estoy corriendo:

Linux irimi 3.10.37-1-MANJARO #1 SMP Mon Apr 14 20:56:29 UTC 2014 x86_64 GNU/Linux

también conocido como una distribución actualizada de Manjaro Linux. El shell que uso es: /bin/bashversión 4.3.8(1)-release.

El contenido de mi SHELLOPTSvariable de entorno es:

braceexpand:emacs:hashall:histexpand:history:interactive-comments:monitor

mi BASHOPTSvariable de entorno es:

cdspell:checkwinsize:cmdhist:complete_fullquote:dotglob:expand_aliases:extglob:extquote:force_fignore:histappend:hostcomplete:interactive_comments:nocaseglob:progcomp:promptvars:sourcepath

Nuevamente, cualquier ayuda para intentar depurar esto sería muy apreciada.

Respuesta1

Hay una trampa con ely/opalabras clave en find. oraplicado a todos los siguientes parámetros, incluida la acción ( -lsen su ejemplo). andLas expresiones sin or(o adjuntas con and) se evalúan en orden de lectura con una parada final como falsa. No hay implicit ().

Entonces el comando find POD -type f -name *.mp3 -or -name *.ogg -lssignifica,

  • buscar archivos (comenzando desde el directorio POD) --- si no se encuentra ningún archivo: DETENER
  • de lo contrario (archivo encontrado) verifique la coincidencia del patrón *.mp3 --- si el patrón coincide: ¡DETÉNGASE! (porque ORse aplica desde aquí y solo si el comando anterior falló (pero solo el comando anterior, no los grupos de comandos anteriores)

y debido a que agrega una declaración de ejecución ( -ls,, ....) en la línea de comando -exec, -printno hay ningún -printcomando implícito y, por lo tanto, no hay nada que ejecutar si 1) todas las condiciones de 1) son verdaderas (el archivo y el patrón coinciden). Si elimina el último, -lshabrá un implícito -printdistribuido al final de cada rama de condición.

  • de lo contrario, si el patrón no coincide, busque nada (archivo/directorio) que coincida con el patrón *.oggy enumérelos ( -lsno es un comando de condición, se ejecuta solo si el comando/prueba anterior "patrón *.ogges verdadero). Pero debido a 1), 2) se evalúa solo para archivos que NO sean mp3. Si no tiene .oggarchivos, no verá nada.

Solución 1 repetir el comando de ejecución en cada rama lógica

   find POD -type f -name "*.mp3" -ls -or -name "*.ogg" -ls

Solución 2agregar paréntesis (protegido por shell)

   find POD -type f \( -name "*.mp3" -ls -or -name "*.ogg" \) -ls

Nota debe proteger los patrones para evitar la evaluación de patrones de shell en el directorio actual.

Respuesta2

Creo que se debe al orden de evaluación (falta de precedencia explícita), por ejemplo, si

-name '*.mp3' -o -name '*.ogg' -ls

luego, si -name '*.ogg'se evalúa como falso, la lsacción no se ejecuta. Puede obtener el comportamiento esperado agrupando sus expresiones OR usando paréntesis; por ejemplo, si

$ ls tests
file1.mp3  file2.mp3  file3.mp3

Entonces

$ find tests \( -name '*.mp3' -o -name '*.ogg' \) -print
tests/file3.mp3
tests/file1.mp3
tests/file2.mp3

mientras

$ find tests -name '*.mp3' -o -name '*.ogg' -print

no produce ninguna salida. Tenga en cuenta que

$ find tests -name '*.mp3' -o -name '*.ogg'

es un caso especial porque implícitamente se trata como

$ find tests \( -name '*.mp3' -o -name '*.ogg' \) -print

También tenga en cuenta que es una buena práctica citar o escapar de los globos del shell en un findcomando para evitar que el shell los expanda; consulte la NON-BUGSsección de la página de manual de búsqueda.

información relacionada