前回からだいぶ間が空いてしまいましたが、今日こそExコマンドについて、あんまりVimが得意でないそこのあなたのために書きます(得意な方は間違っていたらツッコミを…)
Exコマンドの基本
Exコマンドは、Vimを一度でも使ったことがある人なら必ずお世話になっています(その意味で、使用頻度はノーマルモードの次、ヘタしたらインサートモードより上ということもありえます、文字を消すだけならインサートモードに入る必要もないので)。そう、Vimを閉じるときに使う:q
です。あれは:quit
の省略形ですが、立派なExコマンドです。
Exコマンドを入力するには:
をノーマルモードで押します。すると画面の一番下にカーソルが移動するので(コマンドラインといいます)、そこにコマンドを入力してEnterを押せばコマンドが実行されます。アラ簡単。
置換を試す
では、最も使われるコマンドの一つであろう、substitute
コマンドを実行してみましょう。といっても、substitute
では長すぎるので普通はs
が使われますので、そちらで行きましょう。foofoo
という内容のテキストを適当に作り、以下のコマンドを実行します。
:s/foo/bar
…おや、確かに置換は実行されましたが、barfoo
となってしまいました。実はsubstitute
は最初の一回のマッチだけ置換し、残りは置換しないのです。
この動作を変更するには、コマンドの最後に/g
を追加します。ノーマルモードでu
を押して置換を取り消し、以下のコマンドを実行します。
:s/foo/bar/g
どうでしょうか、うまくbarbar
の結果が得られたでしょうか。
範囲指定
さらに試してみましょう。
以下の内容のテキストを用意します。
hoge
fuga
foo
bar
そしてカーソルをhoge
の行に移動させ、以下のコマンドを実行します。
:s/f/z/g
さて結果は…おや、変わっていないですね。実はこれがExコマンドの弱点、今いる行にしか効果がないのです。もともとVim(というより前身のVi)がラインエディタなので、そういう制約があるのだと思われます。
しかし、21世紀でも現役バリバリのエディタであるVim、そこは(少々不格好ですが)しっかりと対応しています。先ほどの置換コマンドをファイル全体に適用させてみましょう。
Exコマンドの書式は
:[range]Command
という書式です。そしてファイル全体を表すには%
を使います。よって、ファイル全体に対して置換する際のコマンドは
:%s/f/z/g
となります。
ね、簡単でしょう?
続・範囲指定
範囲の指定方法は%
以外にもたくさんあります。むしろ、%
の指定は方法としては特殊な部類に入ります(が、多用されるので自然とおぼえます)。最も汎用的な説明としては、行指定子,行指定子
となります。行指定子には数字の他に正規表現を使うこともできます。さらにオフセットも使えるために異常なほど高度な範囲指定も行えます。例えば、「5行目から下、最初にfoobar
という文字列が出現する行の2行上まで」であれば
:5,/foobar/-3
のように書けます(-3
となっているのは、該当行を-1とカウントしているためです)。
…とまあ仰々しく説明しましたが、ぶっちゃけ、使用頻度としては%
がダントツ一番なため、それだけ覚えましょう。
ビジュアルモードと組み合わせる
…おっと、一つ忘れていました。範囲指定をするのに書式を使って指定するのは慣れれば速くてクールだし、何よりハッカーっぽいのですが、実際問題として、範囲というのは人間の目に見えるものなので、それをインタラクティブに表わしてくれる、ようするにマウスで範囲選択するみたいに指定できると便利ですよね。まあ、Vimmerとしては範囲選択にマウスを使った時点で敗北感を噛みしめるわけですが、範囲選択とハイライトをインタラクティブに行えるモードがVimには用意されています。それがビジュアルモードです。
このモードはその説明だけで本の1章に値するほどのものですが、ここではあくまでExコマンドの説明に必要な分にとどめておきます。
ノーマルモードでv
を押すとビジュアルモードに移行しますので、w
とかを押して適当にカーソルを移動させましょう。すると、移動した部分がハイライトされていると思います。ある程度ハイライトされた部分が大きくなったら、:
を押しましょう。すると…
おや、コマンドラインに:'<,'>
と表示されていますね。これは、今ビジュアルモードで選択した部分がすでに範囲指定されている状態であることを意味しています。続けて置換コマンドを実行すると、範囲内のみが置換の対象となることがわかるかと思います。
これは実際非常に便利です。というのは、実際のプログラミングにおいては、置換したい部分が事前にハッキリしていることは稀であり、かつ微妙に散らばっている場合が多いからです。そんな場合は、事前に範囲を綿密に考えてからやるより、ビジュアルモードのままファイル内を移動し、ここだと思ったタイミングで置換するほうが効率的な場合も多いと思います。
外部コマンドを使ってみる
(以下は微妙にオマケっぽいです)
ところで、コマンドラインと言えば当然、シェルが思い浮かびます(ですよね?)。シェルのコマンドはVimで使えるのでしょうか。例えば、
:pwd
おお、動いた。なんだ、できるんじゃん。じゃあ、
:ls
!?
なんかよくわかんないのが出力された!
実はこのコマンド、listはlistでも、バッファーのリストを表示するコマンドなんですね(バッファーというのはこの場合は開いているファイルのことです)。いやでも、俺はカレントディレクトリのファイル一覧が見たいんだ!という人のためにVimが用意してくれている方法はこちら。
:!ls
出力が画面下方に表示されたと思います。今度はちゃんと期待通りでしたね。ちなみにオプションも渡せますので、
:!ls -la
とすることもできます。画面が出力に埋め尽くされると思いますが…
よく使うコマンドリスト
せっかくなのでよく使うコマンドを挙げておきます。
コマンド()内は省略可 | 説明 |
---|---|
q(uit) | 言わずと知れた終了コマンド |
w(rite) | これも必須、保存コマンド |
s(ubstitute) | 置換コマンド、範囲指定と合わせて |
h(elp) | ヘルプを見ます、ヘルプ重要 |
ver(sion) | バージョン情報、どの機能が有効化されているか確かめるのに便利 |
reg(isters) | レジスタの一覧を表示します。コピペ時に便利 |
この記事を最後まで呼んでくださった上級者の方は、自分でよく使うコマンドを教えてくださいー。