开发者

How do I get fine-grained undo in Vim

I find Vim's undo to be a bit too coarse. E.g. if I type something like this:

a // to go into edit mode
to be or not to ve
<es开发者_如何学运维c> // to exit insert mode

Oops! I made a typo. I want to start undoing so I press u, but then it clears the whole line. Is there a way to undo word-by-word or character-by-character?


You can break undos via :help i_ctrl-g_u. You can map this if you want for every character, but that might a little bit complicated. Mapping this to space button is a way.

:inoremap <Space> <Space><C-g>u

After that every word can be undo via u


So as you see from the others what you are asking for doesn't exist in Vi (AFAIK).

Undo undoes what your last action was. If your last action was to enter insert mode and then add a line and then exit insert mode. That will be undone, however if from the default mode you hit the "x" key then you will delete 1 character or if in visual mode with text selected the text will be deleted. If you hit undo then you will restore that one character or the text that was selected.

...You should think of this as an action, and actions can be atomically undone or restored

As mentioned previously if you wish to delete the previous word then you should be able to hit Ctrl + w and delete the previous word while remaining in insert mode.

If you exit insert mode you can navigate (motion) back a word with "b" forward a word with "w" to the end of a word with "e", and can cut (which leaves you in insert mode) with "c" or delete with "d". Both actions cut and delete can accept a motion following them so you can delete the current word / up to the next word with "dw" or cut the previous word with "cb"

This concept becomes more useful when you remember to use the "." command (in normal mode). This command is to repeat the last action. I have used this many times to find and replace a small group of words in a file (It is especially useful if you are paranoid about changing too much). The scenario would be the following:

File:

This is my post

really it is a test

this is the middle

This is the end

if I wanted to replace "is" with "was" I could write: %s/\<is\>/was/g

however if I wanted to change the first line and the third line "is" to "was" (and I didn't know their line numbers, and I wanted to see if there were any other places I wanted to change is to was I could type "/is"

hit "n" until I reach the place I want substituted, and then hit "cw" and type "was" I can now hit "n" until I reach another place I want substituted and hit ".", and that will replace "is" with "was" (Note: my search string didn't limit to the word "is", just the two characters "is" so "This" & "this" will match in this case)


No, it is not possible and is actually not necessary either. Vim has a million ways of dealing with that. Try cb for example. Or bC. Or brb. Or Tspace to jump back instead of b. Or ciw.

You can, of course use most of these solutions in insert mode (by pressing CTRLo first), or bind one to your favorite key combination (:help map and :help imap).


On Linux, using control-w while in input mode deletes the last 'word'.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜