1

I often use M-x replace-regexp and M-x occur with some fixed regexp pattern and replacement string on many files.

Doing it manually by opening each file in an Emacs buffer and hitting the keys is very tedious. I was wondering how to write an Elisp function to use as a script, which I can apply to each file?

  • See also multi-occur. – Drew Nov 13 '18 at 15:16
  • 1
    You could write a macro that opens files from dired, edits them, and goes back to it. You can move by marked files in dired with M-{ and M-}. – DoMiNeLa10 Nov 13 '18 at 18:42
  • If you are working on multiple files, I'd recommend going to the shell, and using sed/awk/perl/python/whatever. – nega Nov 13 '18 at 22:47
2

For replace-regexp in many files, select the files in Dired and press Q to run dired-do-find-regexp-and-replace. See also the FAQ entry.

For the equivalent of occur in many files, you can use A (dired-do-find-regexp) in Dired. Another solution that doesn't use Dired is the grep functions and its variants, where you select files with shell wildcards. Variants include grep-find to search in subdirectories recursively, and (in recent Emacs versions) zgrep to search in compressed files. You can edit the command line to use other shell commands.

For the equivalent of occur in multiple buffers (i.e. files that are already open), there's multi-occur-in-matching-buffers. There are other variants that require entering buffer or file names one by one, but I find those inconvenient.

2

One way this can be accomplished is by using dired. Here's an article from Xah Lee on how to use dired to find and replace across files: http://ergoemacs.org/emacs/find_replace_inter.html

In short, open dired and place the cursor on the directory in which you wish to find and replace. Press Q to start up the query replace prompt. Enter your search pattern and replacement and Emacs will open an *xref* buffer containing all the matches. It will also begin going through each match, opening the buffer, and querying if you'd like to replace it. From the article:

Type y to replace current highlighted occurrence. (emacs will then jump to next one.)
Type n to skip.
Type Ctrl+g to abort the whole find/replace.
Type ! to replace all occurrences in current file without more asking.
Type N to skip all possible replacement for rest of the current file.
Type Y to do the replacement on all files without further asking.
1

You might try using rgrep to find the regexp, then in the results buffer enable wgrep-mode (M-x wgrep-change-to-wgrep-mode, or C-c C-p).

This will allow you to edit (replace) the regexp directly from within the results buffer, bypassing the need to open each file individually.

When the replacement is complete, press C-c C-c to apply the changes to the files, and M-x wgrep-save-all-buffers to save the changes.

  • Chris
  • n.b. wgrep is a third-party library you will need to install (and it's great, so you should do that). – phils Nov 15 '18 at 0:58

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.