前回は、Vimのビジュアルモードでテキスト選択を行う方法を紹介した。ビジュアルモードはオリジナルのViには存在していない機能であり、Vi系の他のエディタも備えていないものが多い。つまり、ビジュアルモードはVimを代表する機能であり、Vimを便利にしている機能と言える。

そこで、次はビジュアルモードで選択したテキストに対してコマンドを適用する処理を取り上げる。よく使う機能なので、こちらもぜひ覚えていただきたい。

選択とインデント

編集するテキストの種類にもよるが、中にはインデントを手動で整理する必要があるものがある。この処理はビジュアルモードを使わなくても既存の置換機能だけで実現できるが、ビジュアルモードと組み合わせると行番号を考えることなく、感覚で作業できるようになるので覚えてもらえればと思う。以下、手順を紹介しよう。

まず、次のような状態のテキストファイルを考えてみてほしい。29行目から55行目までが適切にインデントされておらず、若干悲しいことになっている。

  • インデントが不適切なXMLファイルのサンプル

    インデントが不適切なXMLファイルのサンプル

Vで次のように行レベルで29行目から55行目までを選択する。

  • Vで行選択(29行目〜55行目)

    Vで行選択(29行目~55行目)

この状態で「:s/^/ /」と入力すると、次のようにコマンドラインに置換命令が入力される。範囲指定の部分が「'<,'>」と自動的に入力されているが、これがビジュアルモードで選択した範囲という意味になっている。

  • :s/^/  /と入力するとVimの表示はこうなる

    :s/^/ /と入力するとVimの表示はこうなる

Enterキーを押すと次のように選択した範囲の行頭にスペースが2つ挿入される。「:s/^/ /」は「^」を「 」に置換せよという意味で、「^」は行頭を意味するので「行頭をスペース2個分に置換せよ→行頭にスペースを2つ挿入せよ」といった意味になる。

  • 選択した範囲の行頭にスペースが2つ追加された

    選択した範囲の行頭にスペースが2つ追加された

今度は30行目から54行目までを行単位のビジュアルモードで選択する。

  • Vで行選択(30行目〜54行目)

    Vで行選択(30行目~54行目)

同じようにコマンドを入力するのだが、次は「:↑」のように入力すると、次のように先程入力したコマンドが表示される。「/ /」を「/ /」に変更する。こうした履歴機能を使うことで、入力を省略することができる。いろいろ試していてコマンド履歴がほかのコマンドで詰まっているという場合は、「:'<↑」のように入力すればよい。これにより、ジュアルモードで選択した対象に対する過去のコマンドが検索結果として表示されるようになる。

  • :↑で先程入力したコマンドを表示させる

    :↑で先程入力したコマンドを表示させる

Enterキーを押せば次のようになる。これで、想定していたインデントに整った。

  • 選択した範囲の行頭にスペースが1つ追加された

    選択した範囲の行頭にスペースが1つ追加された

今度は置換機能を行頭への挿入ではなく、置換機能として使ってみよう。まず、次のように行単位で選択を行う。

  • Vで行選択(30行目〜54行目)

    Vで行選択(30行目~54行目)

「:s/access ref/a href/」のように入力する。

  • :s/access ref/a href/と入力した状態

    :s/access ref/a href/と入力した状態

Enterキーを押すと次のように置換が実行される。

  • 対象の文字列が置換されていることがわかる

    対象の文字列が置換されていることがわかる

インデントを追加するという作業とは逆に、インデントを削除するという処理もよく行われる。例えば、次の例はスペース2つ分インデントが多すぎる場合のサンプルだ。

  • 29行目から55行目までがインデントがスペース2つ分多い

    29行目から55行目までがインデントがスペース2つ分多い

今度はCtrl-vでビジュアル選択を行い、行頭2スペース分だけを選択する。

  • Ctrl-vで行選択(29行目〜55行目)

    Ctrl-vで行選択(29行目~55行目)

xキーを押すと選択した範囲が削除され、次のようにインデントが整った状態になる。

  • インデントが整った状態になった

    インデントが整った状態になった

このようにすごく簡単な操作なのだが、知っていると知っていないのとでは作業の効率に大きな差が生まれる。ビジュアルモードで選択して、その範囲に対してコマンドを適用する、ぜひ覚えておいてほしい。

選択とコマンド

Vimのビジュアルモードは、Vimのコマンドではなく、シェルで実行するコマンドと組み合わせることができる点がさらに強力だ。Vimで編集をしていて「この部分はawkで処理できればなあ」とか「grepで処理できれば楽なのにな」と思うことがあるだろうが、Vimでは可能だ。Vimの応用の幅が一気に広がる瞬間だ。

例えば、次のようなデータが含まれたテキストファイルがあったとする。

  • データファイルのサンプル

    データファイルのサンプル

数値データを小さい順に並べ直し、さらに前ゼロ処理して10桁にそろえたいと思ったとする。そうしたら、まず次のように対象を行ごと選択する。

  • Vで編集したいデータを選択

    Vで編集したいデータを選択

ここで、「:!コマンド」のように入力する。利用できるコマンドはプラットフォームにインストールされているコマンドなので、状況によって異なるが、ここではsort --numeric | numfmt 1.\%010gというコマンドを入力している。\%といったように%をエスケープしているのは、%が特別な文字として処理されてしまうためだ。numfmtというコマンドの場合、コマンドラインから入力する場合は1.%010gと指定すればよいが、Vimのコマンドラインモードでは%をエスケープして\%と入力する必要がある。

  • :!コマンド、として実行したいコマンドを入力する

    :!コマンド、として実行したいコマンドを入力する

Enterキーを押すと、次のようにコマンドを適用した結果に置き換わる。テキストファイルの一部に対して任意のコマンドを使った編集ができるわけで、これはかなり便利な機能だ。

  • コマンドの出力結果に置き換わる

    コマンドの出力結果に置き換わる

この機能を知らないと、一旦この部分を別のファイルに保存して、コマンドで処置して、元のファイルに追記して、追記したデータを所定の場所に移動させて、といったような手順を踏んで作業をすることになるだろう。しかし、Vimであればこのように選択した範囲に対してコマンドを適用することができるため、そうした手順は不要だ。

今回取り上げた操作はビジュアルモードで選択しなくても、行範囲を手入力して指定すれば実行できる。しかし、正確に行番号を入力するというのは慣れないとかなりストレスになる操作でもある。ビジュアルモードで逐次選択しながらの作業はストレスの低い作業であり、確認しながら行えるので人間に向いている。便利な機能なのでぜひ覚えてみてはいかがだろうか。