Vim. How to replace a word (string) in several files.

Posted in apps, howto, vim by pavlo on 15th 2008f May, 2008

I Write this post, because I sometimes search for this functionality by myself. Today happened such a case and after I have read again a little bit of online manuals, I decided to post a snippet.

This is taken from the VIM online help (http://vimdoc.sourceforge.net/htmldoc/usr_12.html)

*12.1*	Replace a word

The substitute command can be used to replace all occurrences of a word with
another word:

	:%s/four/4/g

The "%" range means to replace in all lines.  The "g" flag at the end causes
all words in a line to be replaced.
   This will not do the right thing if your file also contains "thirtyfour".
It would be replaced with "thirty4".  To avoid this, use the "\<" item to
match the start of a word:

	:%s/\<four/4/g

Obviously, this still goes wrong on "fourty".  Use "\>" to match the end of a
word:

	:%s/\<four\>/4/g

If you are programming, you might want to replace "four" in comments, but not
in the code.  Since this is difficult to specify, add the "c" flag to have the
substitute command prompt you for each replacement:

	:%s/\<four\>/4/gc

REPLACING IN SEVERAL FILES

Suppose you want to replace a word in more than one file.  You could edit each
file and type the command manually.  It's a lot faster to use record and
playback.
   Let's assume you have a directory with C++ files, all ending in ".cpp".
There is a function called "GetResp" that you want to rename to "GetAnswer".

	vim *.cpp		Start Vim, defining the argument list to
				contain all the C++ files.  You are now in the
				first file.
	qq			Start recording into the q register
	:%s/\<GetResp\>/GetAnswer/g
				Do the replacements in the first file.
	:wnext			Write this file and move to the next one.
	q			Stop recording.
	@q			Execute the q register.  This will replay the
				substitution and ":wnext".  You can verify
				that this doesn't produce an error message.
	999@q 			Execute the q register on the remaining files. 

At the last file you will get an error message, because ":wnext" cannot move
to the next file.  This stops the execution, and everything is done.

	Note:
	When playing back a recorded sequence, an error stops the execution.
	Therefore, make sure you don't get an error message when recording.

There is one catch: If one of the .cpp files does not contain the word
"GetResp", you will get an error and replacing will stop.  To avoid this, add
the "e" flag to the substitute command:

	:%s/\<GetResp\>/GetAnswer/ge

The "e" flag tells ":substitute" that not finding a match is not an error.
About these ads

7 Responses

Subscribe to comments with RSS.

  1. ves said, on 28th 2008f June, 2008 at 9:01

    Wouldn’t it be a bit easier to just use the tabdo (or bufdo) commands? :)

  2. madyogi said, on 30th 2008f June, 2008 at 9:53

    indeed, tabdo/bufdo are really better for this task. I haven’t seen these before. But thank you for pointing this out. The syntax here (using the substitute example above) would be:
    :tabdo s/\/4/g
    :bufdo s/\/4/g
    For more, one can read http://vimdoc.sourceforge.net/htmldoc/tabpage.html#:tabdo and http://vimdoc.sourceforge.net/htmldoc/windows.html#:bufdo

  3. madyogi said, on 30th 2008f June, 2008 at 10:05

    sorry, the code should look something like this:
    :bufdo! %s/\<four\>/4/g

    The other issue is, that you have to write the changes down, after you issued a bufdo! command. One can make it also using bufdo:
    :bufdo! w

  4. Mike said, on 15th 2008f July, 2008 at 20:06

    Stumbled upon your site while searching for exactly this functionality. Lots of handy tips in here!
    From some experimenting that I just finished, I think the ideal solution is a single bufdo command like so:

    :bufdo %s/\/4/g | w

    The pipe allows you to use additional commands per buffer

    Cheers!

  5. Tilo said, on 21st 2009f January, 2009 at 12:49

    Very helpful stuff, exactly what i was looking for – thanks a lot guys.

  6. Andrej P. Sysoev said, on 6th 2010f May, 2010 at 22:04

    Example:
    :args *.[ch]
    :argdo %s/\/My_Foo/ge | update
    This changes the word “my_foo” to “My_Foo” in all *.c and *.h files. The “e”
    flag is used for the “:substitute” command to avoid an error for files where
    “my_foo” isn’t used. “:update” writes the file only if changes were made.

    (http://vimdoc.sourceforge.net/htmldoc/editing.html#:argdo)

  7. ABC said, on 6th 2012f December, 2012 at 6:52

    Great answers


Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Follow

Get every new post delivered to your Inbox.

%d bloggers like this: