Vim で 2 つの複数行のテキスト ブロックを結合する方法を教えてください。質問する

Vim で 2 つの複数行のテキスト ブロックを結合する方法を教えてください。質問する

Vim で 2 つの行ブロックを結合したいと思います。つまり、行 kから 行lを取得し、行mから 行nに追加します。疑似コードによる説明がお好みの場合は、次のようにします[line[k+i] + line[m+i] for i in range(min(l-k, n-m)+1)]

例えば、

abc
def
...

123
45
...

なるべきです

abc123
def45

手動で 1 行ずつコピーして貼り付けることなく、これを行う良い方法はありますか?

ベストアンサー1

確かに、これらすべてを 1 回のコピー/貼り付け (ブロック モード選択を使用) で実行できますが、それは望んでいることではないと思います。

これを単にコマンド

:5,8del | let l=split(@") | 1,4s/$/\=remove(l,0)/

変身する

work it 
make it 
do it 
makes us 
harder
better
faster
stronger
~

の中へ

work it harder
make it better
do it faster
makes us stronger
~

更新:これほど多くの賛成票を得た回答には、より徹底した説明が必要です。

Vimでは、パイプ文字(|)を使用して複数のExコマンドを連結することができるので、上記は以下と同等です。

:5,8del
:let l=split(@")
:1,4s/$/\=remove(l,0)/

多くの Ex コマンドは、プレフィックス引数として行の範囲を受け入れます。上記の例では、5,8の前のdelと の1,4前の がs///、コマンドが操作される行を指定します。

del指定された行を削除します。レジスタ引数を取ることもできますが、指定されていない場合は、@"通常モードでの削除と同様に、行を名前のないレジスタ にダンプします。let l=split(@")次に、削除された行をデフォルトの区切り文字である空白を使用してリストに分割します。削除された行に空白が含まれている入力で適切に機能するには、次のようにします。

more than 
hour 
our 
never 
ever
after
work is
over
~

「work is」が 2 つのリスト要素に分割されるのを防ぐには、別の区切り文字を指定する必要がありますlet l=split(@","\n")

最後に、置換 でs/$/\=remove(l,0)/、各行の末尾 ( $) を式 の値に置き換えますremove(l,0)remove(l,0)はリスト を変更しl、最初の要素を削除して返します。これにより、削除された行を読み取った順序で置き換えることができます。 を使用すると、削除された行を逆の順序で置き換えることもできますremove(l,-1)

おすすめ記事