テキストがあるとしましょう。ビジュアルモードに入り、テキストを選択します。強調表示されたテキストをすばやく検索して別のテキストに置き換えるにはどうすればよいですか?
テキストがあるとしましょう。ビジュアルモードに入り、テキストを選択します。強調表示されたテキストをすばやく検索して別のテキストに置き換えるにはどうすればよいですか?
回答:
以下を実行するか、あなたの中に入れてみてください .vimrc
vnoremap <C-r> "hy:%s/<C-r>h//gc<left><left><left>
ビジュアルモードでctrl+ rを押すと、置換するテキストを入力するように求められます。を押してenter、に同意yまたは拒否する各変更を確認しnます。
このコマンドはレジスターをオーバーライドするh
ため、使用しないレジスターを(h
上記のコマンドで別の小文字に変更することにより)選択できます。
vmap * y:let @/ = @"<CR>
選択された部分が強調表示されます。
<left><left><left>
何ですか?
c
からgc
、あなたはまたの1削除する必要があります<left>
行の末尾からのを。
(hレジスタを上書きせずに)視覚的に強調表示されたテキストを検索し、端末依存の+レジスタを使用せずに、このすばやく簡単なマッピング検索を実行します。
" search for visually hightlighted text
vnoremap <c-f> y<ESC>/<c-r>"<CR>
ctrl-fが気に入らない場合は、好みに変更してください
テキストが強調表示されたら、s
次のように入力するだけでいつでも変更を行うことができます。
%s//<your-replacement-string>
... s
コマンドの空の検索は、最後に検索された文字列を使用するためです。
control+f
常に次の文字と視覚的に選択した文字を選択します。何か案は?
%s//<your-replacement-string>
のようなものを強調するために動作しないようです/tmp/file
。それはちょうどなる<your-replacement-string>/tmp/file
これも機能します(少なくとも1行の選択/特殊文字を含まない選択の場合)
y
:s/<C-r>0/
0
ヤンクレジスタです。
他の人が述べたように、これを行うにはより速い方法がありますが、Vim(私のように)を学び始めたばかりの場合、これは「一般的な」方法の1つです。
//編集:タブや改行などの/
文字または選択範囲に文字がある場合、「登録」アプローチが失敗することに気づきました(:s
コマンドを機能させるために、これらの文字を手動で処理する必要があります)。
ビジュアルセレクションに特殊文字が含まれていない限り、受け入れられた回答は適切に機能します。2つのスクリプト(Jeremy Cantrellの投稿とPeter Oddingのスクリプト)を組み合わせて、特殊な正規表現文字が含まれている場合でも、検索したい文字列を視覚的に選択できるコマンドを作成しました。
" Escape special characters in a string for exact matching.
" This is useful to copying strings from the file to the search tool
" Based on this - http://peterodding.com/code/vim/profile/autoload/xolox/escape.vim
function! EscapeString (string)
let string=a:string
" Escape regex characters
let string = escape(string, '^$.*\/~[]')
" Escape the line endings
let string = substitute(string, '\n', '\\n', 'g')
return string
endfunction
" Get the current visual block for search and replaces
" This function passed the visual block through a string escape function
" Based on this - /programming/676600/vim-replace-selected-text/677918#677918
function! GetVisual() range
" Save the current register and clipboard
let reg_save = getreg('"')
let regtype_save = getregtype('"')
let cb_save = &clipboard
set clipboard&
" Put the current visual selection in the " register
normal! ""gvy
let selection = getreg('"')
" Put the saved registers and clipboards back
call setreg('"', reg_save, regtype_save)
let &clipboard = cb_save
"Escape any special characters in the selection
let escaped_selection = EscapeString(selection)
return escaped_selection
endfunction
" Start the find and replace command across the entire file
vmap <leader>z <Esc>:%s/<c-r>=GetVisual()<cr>/
誰にとっても便利な場合は、これをvimrcに含めました。
vmap <C-r> <Esc>:%s/<c-r>=GetVisual()<cr>//g<left><left>
ファイルのすべてを置き換えるだけです)
Vim 7.4以降gn
では、現在の検索パターンに一致するテキストの領域を選択するモーションを使用できます。
を使用cgn
して現在選択されている一致のテキストを変更した後(またはdgn
削除した後)、通常モードでは.
、コマンドを繰り返して次の一致を操作できます。
この機能を示すVimcastのエピソードがあります。
Mykola Golubyev、ヒントをありがとう!以下では、「+」レジスタを使用します(端末によって異なります)。ハイライトされたテキストがすでに含まれているため、「h」レジスタを使用する必要はありません。
vnoremap <C-r> <Esc>:%s/<C-r>+//gc<left><left><left>
http://vim.wikia.com/wiki/Search_and_replace_in_a_visual_selectionから:
テキストが視覚的に選択されているときに、:を押してコマンドを入力します。コマンドラインは自動的に範囲を入力します:
:'<,'>
s / red / green / gなどのコマンドを入力して、最後のビジュアル選択のすべての行で各赤を緑に置き換えることができます。コマンドは次のように表示されます。
:'<,'>s/red/green/g
以前に選択したブロックに対してExコマンドを繰り返すには、:履歴を使用します。つまり、:を押してから、前のコマンドを編集します。
私はこれを私のvimrcに持っています:
function! GetVisual() range
let reg_save = getreg('"')
let regtype_save = getregtype('"')
let cb_save = &clipboard
set clipboard&
normal! ""gvy
let selection = getreg('"')
call setreg('"', reg_save, regtype_save)
let &clipboard = cb_save
return selection
endfunction
vmap <leader>z :%s/<c-r>=GetVisual()<cr>/
これは、視覚的な選択を取得し、それを使用して置換コマンドを開始します。
編集:これは複数行のビジュアル選択では機能しないことを指摘しておきます。GetVisual()はそれを返すことに問題はありませんが、コマンドラインに適切に配置する方法がわかりません。誰か私がこれを行う方法についてのヒントがあれば、コメントしてください。
他の回答も良いですが、特殊文字をエスケープしません。@brian kennedy の答えはエスケープする方法を示していますが、多くのコードが必要です。たとえばURLの場合、エスケープは必須です。そうしないと、「:」で検索が停止します。
vim.fandom.com/wiki/Search_for_visually_selected_textに記述されているように、ワンライナーを使用して一部の文字を検索およびエスケープできます。あなたはあなたが望む文字をエスケープすることができます、私はエスケープすることを選びました/\:
:
vnoremap // y/\V<C-R>=escape(@",'/\:')<CR><CR>
このマップでは//
、ビジュアルモードでを押して、バッファー全体で現在選択されているテキストを検索する必要があります。
これの私のお気に入りのショートバージョンは
vnoremap s / y:s / "/
次に、選択を強調表示し、s /を押すだけで、その置換コマンドを開始できます。
"
リテラルとして扱われ、私にはうまくいきませんでした。<c-r>"
でも働いた
例1.選択を星で囲み、カーソルを選択の先頭に置きます。
:%s,\%#\%V\_.*\%V/,**&**,c
例2.選択したテキストをbase64でパイプ処理します。
:%s!\%#\%V\_.*\%V!\=system("base64 -w 0",@")!c
説明LHS:
\%# matches cursor
\%V matches inside the selection only
\_. matches any character.
\_.* matches beginning to end of selection.
説明RHS:
\=expr() Replace match with result of expr() for each substitution.
そもそも単語を入力し直さなくても、Vimに単語を置き換える組み込みの方法があることを望んでいました。ありますが、単語境界文字までのテキストに対してのみ機能します。
単語の上にマウスを置いたら、*
または#
を押して単語を強調表示し、その単語の次/前の場所にジャンプします(ファイル内の場所を変更したくない場合は、反対のキーを押して場所に戻りますあなたはちょうどでした)。
それから単にタイプしてください:
%s//<your-replacement-string>
他の人の答えで述べたように%s
、スラッシュの間に空白のエントリを受け取った場合は、以前に検索された単語を使用します。*
またはを押すと#
、カーソルの下の単語が検索され、最後に検索された単語になります。
結局のところ、これを実行するのは6回または7回のキーストローク+置換ワードの長さだけであり、マクロの編集やの編集は必要ありません.vimrc
。
c
in を省略するとgc
、バッファー全体で一度に置換が行われます。間違えて元に戻したい場合はu
、コマンドモードで入力してください。私はこの方法が好きです(置換のそれぞれを確認するよりもc
モディファイアで発生します)。