複数のファイルの内容の一括置換

 複数のファイルの中の単語を置換したい。Perl の置換を利用する。例えば Hoge, hoge を Hage, hage に変換した場合。

$ perl -i -p -e 's/(H|h)oge/$1age/g' input.file
$ perl -i'.back' -p -e 's/(H|h)oge/$1age/g' input.file # バックアップファイル付き

 以下オプションについて。オプションについて詳しい説明が欲しい場合は

$ perldoc perlrun

で調べられる。

-e

 一行プログラム。セミコロンで区切ることで文はいくつも書ける。変数も使える。

$ perl -e '$a = 2; print "hoge" x $2, "\n";'

で hogehoge と出力される。このオプションを指定した場合、引数にプログラムファイルは指定できない。

-p

 与えられたプログラム(-eによる一行プログラムやプログラムファイル)の外側に以下のようなループがあるのと同じような動作をする。

while (<>) {
  # ここに与えたプログラム
  print $_;
}

# 厳密には以下
LINE:
  while (<>) {
    # 与えられたプログラム
  } continue {
    print or die "-p destination: $!\n";
  }

このオプションを使うことで、ファイルの全ての行に対して操作したものを出力できる。行番号を付けたり、置換を行ったり。

-i[extension]

 -p オプションだけでは複数のファイルが与えられたとき、ダイヤモンド演算子 <> がつなげて処理するので、連続的に標準出力に出される。-iオプションを与えてやると個別にファイルが処理され、標準出力はそのファイル自身になる。ファイルのバックアップファイルを作っておきたい場合は extension を指定してやる。

$ perl -i'.back' -p -e 's/bar/baz' fileA fileB fileC
$ perl -i'orig_*' -p -e 's/bar/baz' fileA fileB fileC

extension中に*が使われ無かった場合、extensionは元のファイル名のサフィックスとして足され、*が一つ以上ある場合、*はファイル名と置換される(ただしフルパスが*に入るので注意)。