Hacer que la opción -exec en find funcione

Hacer que la opción -exec en find funcione

Estoy intentando imprimir finduna lista de directorios que contienen archivos distintos de imágenes jpg, pero creo que el uso de la -execopción no funciona. Mi entorno es Cygwin Bash.

$ find ! -iname "*.JPG$" -exec dirname

find: missing argument to `-exec'
$ find ! -iname "*.JPG$" -exec dirname {}

find: missing argument to `-exec'
$ find ! -iname "*.JPG$" -exec dirname;

find: missing argument to `-exec'
$ find ! -iname "*.JPG$" -exec dirname ;

find: missing argument to `-exec'
$ find ! -iname "*.JPG$" -exec dirname {};

find: missing argument to `-exec'

Respuesta1

A -execdebe terminar con a ;o a +. Esto ;hace que el comando se ejecute una vez por cada nombre de archivo encontrado, mientras que +hace que el comando se ejecute una vez para todos los nombres de archivo.

Aquí hay un ejemplo práctico:

find ! -iname "*.JPG" -exec dirname {} \;

Algunas diferencias notables con respecto a sus intentos:

  1. Debe haber un espacio entre {}y\;
  2. Se debe utilizar un carácter ;de escape, porque es un metacarácter de shell.
  3. Como @muru señaló en su respuesta, -inametoma un pegote, no una expresión regular

Respuesta2

Intentar:

find -type f ! -iname "*.JPG" -exec dirname {} \; | sort -u

Notas;

  • Para completar el -execcomando, {}se necesita un para mostrar dónde debe ir el nombre del archivoyse necesita un punto y coma. Debido a que el caparazón se comería un punto y coma simple, tenemos que escapar de él para que pase a find.

  • -inamecoincide con globos, no con expresiones regulares. Entonces, la $entrada final "*.JPG$"probablemente no sea la que deseas.

  • Dijiste que quieres una "lista de directorios que contengan archivos distintos de jpg". En consecuencia, agregué -type fpara estar seguros de que solo miramos directorios que contienen al menos un archivo.

  • Los resultados se pasan sort -upara eliminar duplicados.

Respuesta3

La sintaxis:

-exec [command] ... {} ... ;
-exec [command] ... {} ... +

Dado que ;es parte de la sintaxis del shell, debes escapar de ella para que findla vea como un argumento:

find .. -exec dirname {} \;

Por cierto, -inameno usa expresiones regulares, solo úsalas *.jpgsin el archivo $.


Ahora me sorprende que con GNU find no necesitemos usarlo dirnameen absoluto. En cambio:

find ... -printf "%h\n"

información relacionada