Estoy buscando la mejor manera de buscar y reemplazar (con confirmación) en todos los archivos del proyecto en Vim. Por "archivos de proyecto" me refiero a archivos en el directorio actual, algunos de los cuales no tienen que estar abiertos.
Una forma de hacer esto podría ser simplemente abrir todos los archivos en el directorio actual:
:args ./**
y luego haga la búsqueda y reemplace en todos los archivos abiertos:
:argdo %s/Search/Replace/gce
Sin embargo, cuando hago esto, el uso de memoria de Vim salta de un par de docenas de MB a más de 2 GB, lo que no me funciona.
También tengo instalado el complemento EasyGrep , pero casi nunca funciona, o no encuentra todas las ocurrencias o simplemente se cuelga hasta que presiono CtrlC. Hasta ahora, mi forma preferida de realizar esta tarea es ack-grep para el término de búsqueda, utilizando su ventana de corrección rápida para abrir cualquier archivo que contenga el término y que no se haya abierto antes, y finalmente :bufdo %s/Search/Replace/gce
.
Estoy buscando un complemento bueno y funcional que pueda usarse para esto, o alternativamente un comando / secuencia de comandos que sea más fácil que el que estoy usando ahora.
Respuestas:
Greplace funciona bien para mí.
También hay una versión lista para patógenos en github.
fuente
:Gsearch
y:Gbuffersearch
existen, pero cuando escribo:Greplace
obtengoNot an editor command: Greplace
.:Gsearch [<grep-option(s)>] [[<pattern>] [<filename(s)>]]
por lo que podría hacer una búsqueda recursiva utilizando, por ejemplo::Gsearch -r pattern dir/
La otra gran opción aquí es simplemente no usar vim:
o si tiene alguna forma de generar una lista de archivos, tal vez algo como esto:
¡y así!
fuente
sed
expresiones regulares, que son esencialmente expresiones regulares básicas POSIX.2, pero no exactamente (esto está en la página de manual): permiten que\n
coincida con nuevas líneas y algunas otras cosas similares. Por tanto, son prácticamente iguales agrep
las expresiones regulares.find . -type f | LANG=C xargs sed -i '' 's/SEARCH/REPLACE/g'
EDITAR: use el
cfdo
comando en lugar decdo
para reducir significativamente la cantidad de comandos que se ejecutarán para lograr esto (porquecdo
ejecuta comandos en cada elemento mientrascfdo
ejecuta comandos en cada archivo)Gracias al
cdo
comando agregado recientemente , ahora puede hacer esto en dos comandos simples usando cualquiergrep
herramienta que haya instalado. ¡No se requieren complementos adicionales !:(
cdo
ejecuta el comando dado para cada término en la lista de corrección rápida, que sugrep
comando completa).(Elimine el
c
al final del segundo comando si desea reemplazar cada término de búsqueda sin confirmar cada vez)fuente
:cdo update
para guardar los cambios en todos los archivos.c
al final del segundo comando (solo useg
) para que busque y reemplace sin pedir confirmaciónupdate
, tuve que:cdo %s/<search term>/<replace term>/g | update
Decidí usar ack y Perl para resolver este problema con el fin de aprovechar las expresiones regulares completas de Perl más poderosas en lugar del subconjunto GNU.
Explicación
ack
ACK es una herramienta de línea de comandos impresionante que es una mezcla de
grep
,find
y expresiones regulares de Perl completos (no sólo el subconjunto de GNU). Está escrito en Perl puro, es rápido, tiene resaltado de sintaxis, funciona en Windows y es más amigable para los programadores que las herramientas tradicionales de línea de comandos. Instálelo en Ubuntu consudo apt-get install ack-grep
.xargs
Xargs es una antigua herramienta de línea de comandos de Unix. Lee elementos de la entrada estándar y ejecuta el comando especificado seguido de los elementos leídos para la entrada estándar. Entonces, básicamente, la lista de archivos generados por ack se agrega al final del
perl -pi -E 's/pattern/replacemnt/g'
comando.perl -pi
Perl es un lenguaje de programación. La opción -p hace que Perl cree un bucle alrededor de su programa que itera sobre los argumentos del nombre de archivo. La opción -i hace que Perl edite el archivo en su lugar. Puede modificar esto para crear copias de seguridad. La opción -E hace que Perl ejecute una línea de código especificada como programa. En nuestro caso, el programa es solo una sustitución de expresiones regulares de Perl. Para obtener más información sobre las opciones de la línea de comandos de Perl
perldoc perlrun
. Para obtener más información sobre Perl, consulte http://www.perl.org/ .fuente
tal vez haga esto:
Explicación:
:noautocmd vim /Search/ **/*
⇒ buscar (vim
es una abreviatura devimgrep
) patrón en todos los archivos en todos los subdirectorios de cwd sin activar autocmds (:noautocmd
), por el bien de la velocidad.:set hidden
⇒ permitir que los búferes modificados no se muestren en una ventana (podría estar en su vimrc):cfirst
⇒ saltar al primer resultado de búsquedaqa
⇒ comenzar a grabar una macro en el registro a:%s//Replace/gce
⇒ reemplace todas las apariciones del último patrón de búsqueda (aún/Search/
en ese momento) conReplace
:g
bandera)c
bandera)e
bandera):cnf
⇒ saltar al siguiente archivo en la lista creada por elvim
comandoq
⇒ detener la grabación de la macro1000@a
⇒ reproducir la macro almacenada en el registro 1000 veces:wa
⇒ guardar todos los búferes modificados* EDITAR * Vim 8 vías:
Comenzando con Vim 8, hay una mejor manera de hacerlo, ya que se
:cfdo
repite en todos los archivos de la lista de corrección rápida:fuente
vim
me ha ganado por muchas cosas, creo que me quedaré con PowerGrep con esto.Poblar
:args
desde un comando de shellEs posible (en algunos sistemas operativos 1 )) proporcionar los archivos para
:args
través de un comando de shell.Por ejemplo, si tiene instalado ack 2 ,
le pedirá a ack que devuelva una lista de archivos que contengan 'patrón' y los ponga en la lista de argumentos.
O con grep simple, supongo que sería:
Luego puede usarlo
:argdo
como lo describe el OP:Rellenar
:args
de la lista quickfixConsulte también la respuesta de nelstrom a una pregunta relacionada que describe un comando simple definido por el usuario que llena el arglist de la lista de correcciones rápidas actual. Esto funciona muy bien con muchos comandos y complementos cuya salida termina en la lista de arreglos rápidos (
:vimgrep
,:Ack
3 ,:Ggrep
4 ).La secuencia para realizar una búsqueda en todo el proyecto se podría realizar con:
donde
:Qargs
es la llamada al comando definido por el usuario que llena el arglist de la lista de arreglos rápidos.También encontrará enlaces en la siguiente discusión. a complementos simples que reducen este flujo de trabajo a 2 o 3 comandos.
Enlaces
fuente
Una opción más en 2016, el complemento far.vim :
fuente
Si no le importa introducir dependencia externa, he elaborado un complemento ctrlsf.vim (depende de ack o ag ) para hacer el trabajo.
Puede formatear y mostrar el resultado de la búsqueda de ack / ag, y sincronizar los cambios en el búfer de resultados con los archivos reales del disco.
Tal vez la siguiente demostración explique más
fuente
El paso 1 completa la lista de arreglos rápidos con los elementos que desea. En este caso, se propaga con los términos de búsqueda que desea cambiar a través de
grep
.cfdo
ejecuta el siguiente comando en cada archivo de la lista de corrección rápida. Escriba:help cfdo
para obtener más detalles.s/<search term>/<replace term>/g
reemplaza cada término./g
significa reemplazar cada ocurrencia en el archivo.| update
guarda el archivo después de cada reemplazo.Reuní todo esto en base a esta respuesta y sus comentarios, pero sentí que merecía su propia respuesta ya que está todo en un solo lugar.
fuente
2. :cfdo %s/<search term>/<replace term>/g | update
sin el%
, solo se reemplaza la primera aparición del patrón.%s
funciona en vim regular.Básicamente, quería el reemplazo en un solo comando y, lo que es más importante, dentro de vim.
Basado en la respuesta de @Jefromi, he creado un atajo de teclado, que había configurado en mi archivo .vimrc como este
ahora desde el vim, con un golpe de líder + r obtengo el comando cargado en vim, que edito como a continuación,
Por lo tanto, hago el reemplazo con un solo comando y, lo que es más importante, dentro de vim.
fuente