¿Cómo anteponer texto en masa a los nombres de archivo?

44

Digamos que tengo un directorio lleno de .mdarchivos, todos nombrados varias cosas. Digamos que quería anteponer "texto" al frente de cada nombre de archivo. Así, por ejemplo: archivo a.md, b.mdy c.mdse convertiría en test - a.md, test - b.mdy test - c.md.

¿Cómo lograría esto a través de la línea de comando?

Jesse Atkinson
fuente

Respuestas:

60

One-liner que se puede escribir fácilmente directamente desde la terminal:

for f in *.md; do mv "$f" "test - $f"; done

O reescrito en líneas separadas en lugar de punto y coma:

for f in *.md
do
    mv "$f" "test - $f"
done

Exposición

Sintaxis de for(in sh):

for NAME [in WORDS ... ] ; do COMMANDS; done

Aquí, nuestro NAMEes fy nuestro WORDSson todos los archivos en el directorio actual *.md. Por lo tanto, la variable $fse sustituirá con cada archivo que coincida *.md.

Entonces para a.md:

mv "$f" "test - $f"

se convierte

mv "a.md" "test - a.md"

Las comillas son importantes porque cada nombre de archivo $fpuede contener espacios. De mvlo contrario , pensaría que cada palabra era un archivo separado. Por ejemplo, si no hubiera comillas, y hay un archivo llamado Foo Bar.md, se traduciría como:

mv Foo Bar.md test - Foo Bar.md

que no funcionaría según lo previsto. Pero al incluir $fcomillas, tiene sentido:

mv "Foo Bar.md" "test - Foo Bar.md"

Observando la sintaxis de for, también puede cambiar el nombre de un subconjunto de todos los *.mdarchivos nombrando cada uno explícitamente:

for f in a.md b.md d.md; do mv "$f" "Test - $f"; done

O usando la expansión de shell:

for f in {a,b,d}.md; do mv "$f" "Test - $f"; done
QuasarDonkey
fuente
Esto es exactamente lo que necesitaba ver. ¡Gracias!
Ryan
11

Si tienes prename...

prename 's/^/test - /' *.md

Usando comandos de shell ordinarios:

for file in *.md; do
    mv "$file" "test - $file"
done
Gravedad
fuente
¿Cómo consigo prename?
Gaʀʀʏ
Parece estar preinstalado para mí en Ubuntu 16.04 LTS. ¿Has probado tu administrador de paquetes (es decir, sudo apt-get install)?
Orion751
5

mmv1 , 2 también es una herramienta muy buena para tal tarea, aplicada al trabajo actual, sería

mmv '*.md' 'test - #1.md'

Por supuesto, si solo desea agregar "test -" a a.md, b.md y c.md, pero no a1.md, algo así como

mmv '?.md' 'test - #1.md'

Sería más apropiado.

Realmente puedo sugerirlo, especialmente si tienes muchos de esos problemas.

Si además está buscando una interfaz gráfica, pruebe gprename .

Claudio
fuente
5

En lugar de usar un bucle for, que fallará en los espacios a menos que redefina la variable IFS, recomendaría usar un bucle while combinado con find. Lo siguiente funcionará cuando se ejecute desde el mismo directorio que los archivos

find . -maxdepth 1 -type f -name '*.md' | while read -r file; do
    file=$(basename $file)
    mv "$file" "test - $file"
done

la línea "basename" está allí, de modo que find imprimirá solo el nombre del archivo, sin componentes de ruta, lo que haría que la operación de cambio de nombre se interrumpiera.

Fred Clausen
fuente
2

Sé que es realmente tarde, pero si alguien más está buscando algo como esto, entonces esto funcionó para mí:

rename '' 'name -' *.md
nullptr
fuente
1
simple y directo
user13743
0

Si tienes zshdisponible puedes usar zmv:

autoload zmv
zmv -w '*' 'test - $1'

Puede probar el comando con:

zmv -wn '*' 'test - $1'
  • -n significa funcionamiento en seco, es decir, solo muestra lo que sucederá.
  • -w implícitamente pone paréntesis alrededor de comodines, hace que las referencias posteriores funcionen.
Thor
fuente
0

En bash, agregando "Anteponer texto -" a todos los archivos en la carpeta:

for i in *; do mv "$i" "$(echo $i | sed 's/^/Prepend\ text\ \-\ /')"; done;
Osiris
fuente
Esta es una forma de escritura súper largafor i in *; do mv "$i$" "Prepend text - $i"; done
David Richerby,