2019年7月10日水曜日

ドットコマンドで無名レジスタに入ったテキストを挿入する方法

概要

Vimgolfの問題 Words in parens に取り組んだ。
得られた知識を「ドットコマンドで無名レジスタに入ったテキストを挿入する方法」として解説する。

問題


one two
three

を、以下のように書きかえる

(one) (two)
(three)

解説

この問題では、3つのワードを()で囲えばよい。

方針としては、最初のワードをうまいこと編集し、残りのワードについてもドットコマンドで同じ処理を繰り返せばよいだろう。

こんなコマンドでどうか。
cw(<C-R>")<Esc>w.w.ZZ

  1. cw
    最初のワードoneを削除しインサートモードに入る
    この際、無名レジスタにテキストoneが入る
  2. (
    単純に(を挿入する
  3. <C-R>"
    インサートモードにおいて、無名レジスタの中身を挿入する
  4. )
    単純に)を挿入する
  5. <Esc>
    ノーマルモードに復帰する
  6. w
    次のワードであるtwoの先頭に移動する
  7. .
    先ほどと同じ処理を繰り返す
  8. w
    次のワードであるthreeの先頭に移動する
  9. .
    先ほどと同じ処理を繰り返す
  10. ZZ
    編集内容を保存して終了

結果はどうだろう。
one two three → (one) (one) (one)
あれ、全部oneになっている。

レジスタを覗いてみよう。
:reg .

--- Registers ---
".   (one)

直接テキストoneを入力した場合と同様に解釈されている。
これでは困る。

「直接テキストoneを入力したように記録してほしい」のではなく、「無名レジスタに入ったテキストを入力したと記録してほしい」のだ。

意図した動作をしてもらうには、<C-R>"の代わりに<C-R><C-O>"と入力する※。

すなわち、こんなコマンドである。
cw(<C-R><C-O>")<Esc>w.w.ZZ

これにより、目的は達せられる。
one two three → (one) (two) (three)

レジスタを覗いてみる
:reg .
--- Registers ---
".   (^R^O")

先ほどとは明らかに違っているのが分かる。
打ち込んだキーがそのまま記録されている。


詳しくは :help c_CTRL-R_CTRL-O で。
この解説は、Score: 14 のコメント欄でのやり取りを参考にした。

0 件のコメント:

コメントを投稿

コメント表示は承認制に設定しています