Que longitud Longitud del nombre de archivo? Longitud de la página?
Ignacio Vázquez-Abrams
Respuestas:
18
Suponiendo que está utilizando GNU find(que probablemente es, ya que -iregexes una extensión de GNU a POSIXfind ), -regexy por -iregexdefecto a las expresiones regulares de Emacs, que no reconocen {3,}. Debe especificar un tipo diferente de expresiones regulares utilizando la -regextypeopción; Además, debe ajustar su expresión regular al hecho de que la expresión coincide con la ruta completa:
O con algunas findimplementaciones (las que -regextambién admiten -iname):
find ~ -iname '*???.pdf'
Para números arbitrarios de caracteres en lugar de 3, es donde puede preferir volver a -iregexdonde esté disponible (consulte la respuesta de @Stephen Kitt ) o puede usar zsho ksh93globs:
zsh:
set -o extendedglob # best in ~/.zshrc
printf '%s\n' ~/**/?(#c3,).(#i)pdf(D)
( (D)para considerar archivos ocultos y archivos en directorios ocultos como con find)
(#cx,y)es el zshcomodín equivalente de regexp{x,y}
(#i) para mayúsculas y minúsculas
?comodín estándar para cualquier carácter individual (como regexp .)
**/: cualquier nivel de subdirectorios (incluido 0)
ksh93:
FIGNORE='@(.|..)' # to consider hidden files
set -o globstar
printf '%s\n' **/{3,}(?).~(i:pdf)
@(x|y): operador comodín ksh extendido similar a regexp (x|y).
FIGNORE: variable especial que controla qué archivos son ignorados por los globos. Cuando se establece, no se hace caso omiso de los archivos ocultos, pero aún queremos ignorar las entradas del directorio .y ..donde están presentes.
{x,y}(z)es ksh93el equivalente de regexp z{x,y}.
~(i:...): coincidencia entre mayúsculas y minúsculas.
Los globs tienen algunas ventajas adicionales findaquí, ya que obtienes una lista ordenada (puedes deshabilitar esa clasificación zshcon el oNcalificador glob o usar diferentes criterios de clasificación) y también funciona cuando los nombres de archivo contienen una secuencia de bytes que no forman caracteres válidos (para Por ejemplo, en un entorno local que utiliza el juego de caracteres UTF-8, el findenfoque no informaría de $'St\xE9phane Chazelas - CV.pdfque, dado que \xE9no es un personaje, no coincide con regexp .o comodín ?o *con GNU find).
¿Funcionaría esto para Bash? shopt -s dotglob globstar; printf '%s\n' ~/**/*???.[pP][dD][fF]
wjandrea
7
¿Cómo sé que son archivos PDF?
No lo haces a menos que lo pidas. Claro, estoy siendo pedante, pero no preguntaste sobre los archivos con .pdfsus nombres . El hecho de que un archivo tenga los caracteres .pdfen el nombre de archivo no lo convierte en un archivo PDF .
De hecho, seamos pedantes al respecto: si los últimos cuatro caracteres del nombre de un archivo lo son .pdf, siempre tendrá más de tres caracteres en su nombre .
Entonces, haciendo esto de manera incorrecta , podrías decir:
¿Ves ese segundo? En realidad es un ejecutable. (Lo sé, cambié el nombre). Y también me falta un PDF que podría haber jurado que estaba en el directorio de Documentos ...
$ ls Documents
McLaren 720s Coupe:Order Summary.pdf
Pioneer Premier DEH-P490IB CD Install Manual.PDF
Setup_MagicISO.exe.pdf
Entonces, usando -inamepodríamos encontrarlo, pero aún así aparece este archivo que no es PDF.
Lo que realmente queremos hacer en este caso es examinar el número mágico del archivo con el filecomando. Una opción genera el tipo MIME , que es más fácil de analizar. La findconsulta se convierte en una simple -name "???*".
Usemos el delimitador de dos puntos y busquemos el tipo MIME application/pdf, luego ponmos a cero esa porción e imprimimos el resultado. Tome nota, uno de mis archivos tiene dos puntos en el nombre; así que no puedo pedirle a awk que lo haga ($2==":"){print $1}.
$ find . -type f -name "???*" -print0|xargs -0 file --mime|awk -F: '($NF~"application/pdf"){OFS=":";$NF="";print}'|sed s/:$//
./Documents/McLaren 720s Coupe:Order Summary.pdf
./Documents/Pioneer Premier DEH-P490IB CD Install Manual.PDF
Ahora terminemos por incluir archivos PDF con el nombre ay abc:
$ mkdir Documents/other
$ cp -a Documents/McLaren\ 720s\ Coupe\:Order\ Summary.pdf Documents/other/a
$ cp -a Documents/Pioneer\ Premier\ DEH-P490IB\ CD\ Install\ Manual.PDF Documents/other/abc
$ find . -type f -name "???*" -print0|xargs -0 file --mime|awk -F: '($NF~"application/pdf"){OFS=":";$NF="";print}'|sed s/:$//
./Documents/McLaren 720s Coupe:Order Summary.pdf
./Documents/Pioneer Premier DEH-P490IB CD Install Manual.PDF
./Documents/other/abc
Eso es todo. Sé que probablemente me criticarán por ser terriblemente pedante, pero en mi trabajo con miles de volúmenes NFS para cazar y todo tipo de archivos mal nombrados, desearía que más personas fueran pedantes.
Editado para agregar: en el mundo real, es posible que desee utilizar updatedbpara crear un índice de archivo de búsqueda, en locatelugar de findleer ese índice y en parallellugar de xargsenhebrarlo. Sin embargo, eso está algo fuera del alcance de esta pregunta. También escribí eso con una cara seria. ¿Por qué me importa tanto? Podría estar buscando películas y archivos de audio; o ciertos tipos de fotografías; o ejecutables binarios en un directorio de datos del proyecto.
Si el autor de la pregunta tiene la misma situación que usted, donde hay archivos PDF cuyos nombres no terminan .pdf, su pedantería será muy apreciada. Pero es una situación relativamente inusual (a pesar de su trabajo) y no tenemos ninguna razón para creer que el autor de la pregunta realmente tenga que lidiar con eso, por lo que creo que el punto que está haciendo, aunque válido, es un poco distractor. y creo que la manera contundente en la que lo has expresado empuja la respuesta al ámbito de "(probablemente) no útil". (Solo mi opinión, por supuesto.)
David Z
Como estamos siendo pedantes, ¿cómo manejaría archivos PDF como los políglotas PoC || GTFO ?
Stephen Kitt
@StephenKitt: no estoy seguro de lo que estás preguntando, pero estoy intrigado. A mí me parecen archivos PDF normales con nombres no particularmente originales. ¿Fallarían estos mi solución sugerida?
Rico
@DavidZ No estoy seguro de qué decir a eso. Quiero decir, ¿no es un poco pedante señalar que soy pedante cuando ya lo dije? He aquí por qué no es "no útil": una buena solución para encontrar archivos PDF debería ser una solución adaptable para encontrar scripts, ejecutables binarios, bibliotecas, archivos multimedia, etc. Ni siquiera puedo comenzar a ver cómo adaptaría uno de los otras respuestas para "ejecutables comprimidos de Mach", pero estoy dispuesto a aprender.
Rico
1
@Rich muchos de los PDF también son archivos ZIP, algunos también son imágenes, o incluso máquinas virtuales de arranque ... (Consulte los enlaces de "spoilers" en los primeros números para obtener sugerencias; el resto están documentados en los propios PDF)
Respuestas:
Suponiendo que está utilizando GNU
find
(que probablemente es, ya que-iregex
es una extensión de GNU a POSIXfind
),-regex
y por-iregex
defecto a las expresiones regulares de Emacs, que no reconocen{3,}
. Debe especificar un tipo diferente de expresiones regulares utilizando la-regextype
opción; Además, debe ajustar su expresión regular al hecho de que la expresión coincide con la ruta completa:También debe escapar de
.
modo que coincida con "." en lugar de cualquier personaje:La expresión regular se puede simplificar ya que solo nos interesan tres caracteres que no son "/":
Para completar, con FreeBSD o NetBSD
find
(otra implementación que admite-iregex
, no la tuya, ya.+
que no funcionaría allí sin-E
), escribirías:o:
Sin
-E
, esa es una expresión regular básica (como engrep
) y con-E
una expresión regular extendida (como engrep -E
).Con ast-open's
find
:(eso es expresiones regulares extendidas fuera de la caja).
fuente
Aquí es más fácil con los comodines estándar:
O con algunas
find
implementaciones (las que-regex
también admiten-iname
):Para números arbitrarios de caracteres en lugar de
3
, es donde puede preferir volver a-iregex
donde esté disponible (consulte la respuesta de @Stephen Kitt ) o puede usarzsh
oksh93
globs:zsh
:(
(D)
para considerar archivos ocultos y archivos en directorios ocultos como confind
)(#cx,y)
es elzsh
comodín equivalente de regexp{x,y}
(#i)
para mayúsculas y minúsculas?
comodín estándar para cualquier carácter individual (como regexp.
)**/
: cualquier nivel de subdirectorios (incluido 0)ksh93
:@(x|y)
: operador comodín ksh extendido similar a regexp(x|y)
.FIGNORE
: variable especial que controla qué archivos son ignorados por los globos. Cuando se establece, no se hace caso omiso de los archivos ocultos, pero aún queremos ignorar las entradas del directorio.
y..
donde están presentes.{x,y}(z)
esksh93
el equivalente de regexpz{x,y}
.~(i:...)
: coincidencia entre mayúsculas y minúsculas.Los globs tienen algunas ventajas adicionales
find
aquí, ya que obtienes una lista ordenada (puedes deshabilitar esa clasificaciónzsh
con eloN
calificador glob o usar diferentes criterios de clasificación) y también funciona cuando los nombres de archivo contienen una secuencia de bytes que no forman caracteres válidos (para Por ejemplo, en un entorno local que utiliza el juego de caracteres UTF-8, elfind
enfoque no informaría de$'St\xE9phane Chazelas - CV.pdf
que, dado que\xE9
no es un personaje, no coincide con regexp.
o comodín?
o*
con GNUfind
).fuente
shopt -s dotglob globstar; printf '%s\n' ~/**/*???.[pP][dD][fF]
¿Cómo sé que son archivos PDF?
No lo haces a menos que lo pidas. Claro, estoy siendo pedante, pero no preguntaste sobre los archivos con
.pdf
sus nombres . El hecho de que un archivo tenga los caracteres.pdf
en el nombre de archivo no lo convierte en un archivo PDF .De hecho, seamos pedantes al respecto: si los últimos cuatro caracteres del nombre de un archivo lo son
.pdf
, siempre tendrá más de tres caracteres en su nombre .Entonces, haciendo esto de manera incorrecta , podrías decir:
¿Ves ese segundo? En realidad es un ejecutable. (Lo sé, cambié el nombre). Y también me falta un PDF que podría haber jurado que estaba en el directorio de Documentos ...
Entonces, usando
-iname
podríamos encontrarlo, pero aún así aparece este archivo que no es PDF.Lo que realmente queremos hacer en este caso es examinar el número mágico del archivo con el
file
comando. Una opción genera el tipo MIME , que es más fácil de analizar. Lafind
consulta se convierte en una simple-name "???*"
.Usemos el delimitador de dos puntos y busquemos el tipo MIME
application/pdf
, luego ponmos a cero esa porción e imprimimos el resultado. Tome nota, uno de mis archivos tiene dos puntos en el nombre; así que no puedo pedirle a awk que lo haga($2==":"){print $1}
.Ahora terminemos por incluir archivos PDF con el nombre
a
yabc
:Eso es todo. Sé que probablemente me criticarán por ser terriblemente pedante, pero en mi trabajo con miles de volúmenes NFS para cazar y todo tipo de archivos mal nombrados, desearía que más personas fueran pedantes.
Editado para agregar: en el mundo real, es posible que desee utilizar
updatedb
para crear un índice de archivo de búsqueda, enlocate
lugar defind
leer ese índice y enparallel
lugar dexargs
enhebrarlo. Sin embargo, eso está algo fuera del alcance de esta pregunta. También escribí eso con una cara seria. ¿Por qué me importa tanto? Podría estar buscando películas y archivos de audio; o ciertos tipos de fotografías; o ejecutables binarios en un directorio de datos del proyecto.fuente
.pdf
, su pedantería será muy apreciada. Pero es una situación relativamente inusual (a pesar de su trabajo) y no tenemos ninguna razón para creer que el autor de la pregunta realmente tenga que lidiar con eso, por lo que creo que el punto que está haciendo, aunque válido, es un poco distractor. y creo que la manera contundente en la que lo has expresado empuja la respuesta al ámbito de "(probablemente) no útil". (Solo mi opinión, por supuesto.)