あえていうほどでもないsed入門

Pocket

「これsedでできるんだけど、どうやるんだっけ…」という状況ありますよね。

あなたのためにまとめておきました。

sedってなに?

sedはファイルやパイプラインからデータを受け取り、なんらかの加工をして結果を返します。

マニュアルよるとsedは「stream editor」です。

sedの構文

GNUのマニュアルからの引用ですが、下記になります。

[SCRIPT]とは"s/foo/bar/g"のようなヤツのことです。あとで紹介する"1i foo"や"1d"もそうです。
"-e"オプションで直後に[SCRIPT]が来ることを示します。"-e"が無い場合は、最初のオプションではないパラメータがSCRIPTと見なされます。

また、[INPUTFILE]が存在しない場合、sedは標準入力を読み込みます。

下記の例では、"Hello World"の文字列を受け取り、"World"を"Japan"に変換します。

シングルクオート?ダブルクオート?

上記の例では、[SCRIPT]をダブルクオートで囲いました。これは無くても動きます。

しかしこの記法では、[SCRIPT]にスペースを含めたときに問題が起きます。

ダブルクオートとシングルクオートでは、エスケープ処理の有無に違いがあります。

シングルクオートを使用することでbashによる展開等を行わず、sedに文字列をそのまま渡してあげるイメージですね。
この記事では基本的にダブルクオートを使用します。

sedのバージョン

検証に使用したsedのバージョンです。OSはCentOS 7.1を使用しました。

枯れたツールですのでバージョン間の差異はさほど気にしなくていいですが、GNUとBSDではいくつかの点で挙動が異なりますのでお気をつけください。

この記事ではGNUのsedを対象とします。(お手元のLinuxにはこちらのsedがインストールされているかと思います)

文字列変換の基本

あえて言うほどではないこと

"World"を"Japan"に変換します。先ほどの例と同じです。

最後のgは"すべて"という意味です。gが無い場合は、初めに見つけたものだけを変換します。

ファイルの中身を書き換える

ファイルを渡した場合のデフォルトの出力先は標準出力ですが、"-i"オプションを渡すことでファイルの書き換えができます。

パイプでつなげる

sedの結果は標準出力にでるので、それを利用してパイプで連結させることができます。

ただし、上記のように単純にsedの書き換えをつなげたいだけならば、"-e"を複数使用したほうがよいでしょう。

話は多少それますが、小文字から大文字に変えたいだけであれば下記の記法も使用できます。

変換したい文字列に"/"が含まれている場合

区切り文字を変えましょう。sedやシェル的に特別な意味をもたない記号・文字であれば何でもよいです。
(個人的にはコロン(:)が見やすくておススメです)

文字列の挿入・削除

挿入・削除の基本

基本は置き換えです。

行頭・行末の挿入・削除

行頭・行末に挿入・削除も可能です。
下記の内容のファイル(sample.txt)があるとします。

行の挿入・削除

分量が多くなってきたので、ここからは実行結果を省略しコマンドのみ紹介します。

行の挿入

行の削除

sedと正規表現

使用できる特殊文字

\*, \?, $, ^, \nなどが使用可能です。

すべてを知りたい方はマニュアルをご覧ください。

基本的な使用例

マッチした文字列を削除する例を示します。もちろん文字列の置き換え、行の削除や挿入と組み合わせることができます。

マッチした部分の取り出し

正規表現にマッチした部分を取り出し、その後で使用することができます。

上記では、"id:"に続く文字列が取り出され、それを利用しています。
簡単に説明すると、取り出したい箇所をエスケープした丸かっこでくくると、"\1"で参照可能になります。

また、取り出す箇所を2つ、3つと増やすこともできます。その場合は丸かっこを複数使い、\2,\3などと取り出します。

下記の例では、"/etc/passwd"からuid,gidを取得し、整形して表示しています。

適切な例が思い浮かばず複雑になってしまいましたが、ここで気をつけないといけないのは、
".*"は最短マッチでは無く、".*?"もサポートされていないことです。

sedと最短マッチ

まず下記を見てください。

意図しない結果になってしまいました。先ほど述べたとおり、最短マッチしてくれないわけです。
少し工夫が必要です。

うまくいきました。

[^>]* に注目してください。これは">"を含まない文字列にマッチします。
上記の例でいうと、sedは"<"の次の文字からマッチさせていき、">"を見つけたら、その前でマッチをストップします。

使い方あれこれ

ここまでで触れられなかった使用方法を紹介します。

範囲指定

ファイルの行を指定して、sedに処理をさせることができます。

ここで使用している"1,5"などの箇所は、sedのマニュアルでは"address"と呼ばれます。

行の表示

単純に指定した行を表示させることができます。

エスケープ処理が面倒なときに

SCRIPTの囲みをダブルクオートからシングルクオートに変更します。

大文字・小文字を区別しない

sコマンド(ex:"s/foo/bar/g")のiフラグにより、大文字、小文字に鈍感になります。(case-insensitive)

複数のファイルを処理

引数に複数ファイルを並べることができます

便利パターン

良く使いそうなパターンを紹介します。

むすびに

いかがでしたでしょうか。

みなさまに素敵なsedライフが訪れますように。

参考文献

  • sed a stream editor(GNU のオンラインドキュメント)
  • ブルース・ブリン『入門UNIXシェルプログラミング』山下哲典訳,ソフトバンククリエイティブ
  • Pocket

    Comments are closed, but you can leave a trackback: Trackback URL.