Ответ 1
Greplace хорошо работает для меня.
В github также есть версия, подготовленная к патогену.
Я ищу лучший способ выполнить поиск и замену (с подтверждением) во всех файлах проекта в Vim. Под "файлами проекта" я имею в виду файлы в текущем каталоге, некоторые из которых не должны быть открытыми.
Одним из способов сделать это может быть просто открытие всех файлов в текущем каталоге:
:args ./**
а затем выполните поиск и замену во всех открытых файлах:
:argdo %s/Search/Replace/gce
Однако, когда я это делаю, использование памяти Vim перескакивает с пары десятков МБ на более чем 2 ГБ, что не работает для меня.
У меня также установлен плагин EasyGrep, но он почти никогда не работает/либо он не находит всех вхождений, либо просто зависает, пока не нажимаю Ctrl C. До сих пор мой предпочтительный способ выполнить эту задачу для ack-grep для поискового запроса, используя его окно быстрого открытия, открыть любой файл, содержащий этот термин и ранее не открывшийся, и, наконец, :bufdo %s/Search/Replace/gce
.
Я ищу либо хороший рабочий плагин, который можно использовать для этого, либо, альтернативно, команду/последовательность команд, которые были бы проще, чем тот, который я использую сейчас.
Greplace хорошо работает для меня.
В github также есть версия, подготовленная к патогену.
Другой большой вариант здесь просто не использовать vim:
sed -i 's/pattern/replacement/' <files>
или если у вас есть способ генерации списка файлов, возможно, что-то вроде этого:
find . -name *.cpp | xargs sed -i 's/pattern/replacement/'
grep -rl 'pattern1' | xargs sed -i 's/pattern2/replacement/'
и т.д.
Я решил использовать ack и Perl для решения этой проблемы, чтобы воспользоваться более мощными полными регулярными выражениями Perl, а не подмножеством GNU.
ack -l 'pattern' | xargs perl -pi -E 's/pattern/replacement/g'
ack - это отличный инструмент командной строки, который представляет собой сочетание grep
, find
и полных регулярных выражений (а не только подмножества GNU). Его написанный на чистом Perl, его быстрый, он имеет подсветку синтаксиса, работает на Windows и более дружелюбен к программистам, чем традиционные инструменты командной строки. Установите его на Ubuntu с помощью sudo apt-get install ack-grep
.
Xargs - это старый инструмент командной строки unix. Он считывает элементы со стандартного ввода и выполняет указанную команду, за которой следуют элементы, считанные для стандартного ввода. Таким образом, в основном список файлов, созданных ack, добавляется в конец команды perl -pi -E 's/pattern/replacemnt/g'
.
Perl - это язык программирования. Параметр -p заставляет Perl создавать цикл вокруг вашей программы, который выполняет итерацию по аргументам имени файла. Опция -i заставляет Perl редактировать файл на месте. Вы можете изменить это для создания резервных копий. Параметр -E заставляет Perl выполнять одну строку кода, указанную в качестве программы. В нашем случае программа является просто заменой регулярного выражения Perl. Дополнительные сведения о параметрах командной строки Perl perldoc perlrun
. Для получения дополнительной информации о Perl см. http://www.perl.org/.
может сделать это:
:noautocmd vim /Search/ **/*
:set hidden
:cfirst
qa
:%s//Replace/gce
:cnf
q
[email protected]
:wa
Пояснение:
:noautocmd vim /Search/ **/*
⇒ lookup (vim
is an abbreviation for vimgrep
) pattern in all files in all subdirectories of the cwd without triggering autocmds (:noautocmd
), for speed sake.:set hidden
⇒ allow having modified buffers not displayed in a window (could be in your vimrc):cfirst
⇒ jump to first search resultqa
⇒ start recording a macro into register a:%s//Replace/gce
⇒ replace all occurrences of the last search pattern (still /Search/
at that time) with Replace
:
g
)c
)e
):cnf
⇒ jump to next file in the list created by the vim
commandq
⇒ stop recording macro[email protected]
⇒ play macro stored in register a 1000 times:wa
⇒ save all modified buffers* EDIT * Vim 8 way:
Начиная с Vim 8 есть лучший способ сделать это, так как :cfdo
выполняет итерацию по всем файлам в списке quickfix:
:noautocmd vim /Search/ **/*
:set hidden
:cfdo %s//Replace/gce
:wa
:args
из командной строкиВозможно (в некоторых операционных системах 1)) для отправки файлов :args
с помощью команды оболочки.
Например, если у вас установлен ack 2,
:args `ack -l pattern`
попросит ack вернуть список файлов, содержащих 'pattern', и поместить их в список аргументов.
Или с простым ol 'grep, я предполагаю, что это будет:
:args `grep -lr pattern .`
Затем вы можете просто использовать :argdo
, как описано в OP:
:argdo %s/pattern/replacement/gce
:args
из списка быстрого удаленияТакже проверьте ответ nelstrom на связанный с ним вопрос, описывающий простую пользовательскую команду, которая заполняет список arglist из текущего списка быстрого исправления. Это отлично работает со многими командами и плагинами, выход которых попадает в список быстрого списка (:vimgrep
, :Ack
3:Ggrep
4).
Последовательность выполнения широкомасштабного поиска проекта может быть выполнена с помощью:
:vimgrep /pattern/ **/*
:Qargs
:argdo %s/findme/replacement/gc
где :Qargs
- это вызов пользовательской команды, которая заполняет список arglist из списка quickfix.
Вы также найдете ссылки в последующем обсуждении на простые плагины, которые получают этот рабочий процесс до двух или трех команд.
Благодаря недавно добавленной команде cdo
, вы можете сделать это двумя простыми командами, используя любой инструмент grep
, который вы установили, Никаких дополнительных плагинов не требуется!:
1. :grep <search term>
2. :cdo %s/<search term>/<replace term>/gc
3. (If you want to save the changes in all files) :cdo update
(cdo
выполняет данную команду для каждого термина в списке быстрого исправления, который заполняется вашей командой grep
.)
(Удалите c
в конце 2-й команды, если вы хотите заменить каждый термин поиска, не подтверждая каждый раз)
Еще один вариант в 2016 году, far.vim плагин:
Если вы не возражаете против введения внешней зависимости, я заварил плагин ctrlsf.vim (зависит от ack или ag) для выполнения задания.
Он может форматировать и отображать результат поиска из ack/ag и синхронизировать ваши изменения в буфере результатов с фактическими файлами на диске.
Возможно, следующая демонстрация объясняет больше
В принципе, мне нужна замена в одной команде и, что более важно, внутри самого vim
Основываясь на ответе by @Jefromi, я создал ярлык для клавиатуры, который я установил в моем .vimrc файле, подобном этому
nmap <leader>r :!grep -r -l * \| xargs sed -i -e 's///g'
теперь из vim, на ударе лидера + r Я получаю команду, загруженную в vim, которую я редактирую, как показано ниже,
:!grep -r -l <find> <file pattern> | xargs sed -i -e 's/<find>/<replace>/g'
Следовательно, я делаю замену одной командой и, что более важно, внутри самого vim