SedはシンプルなUNIXプログラムです。それは、ファイルを作成し、編集しません。それは、その入力を通過するデータを変更し、その出力に変更されたデータを提示するだけです。それにもかかわらず、sedはLinuxで遭遇する最も強力なUNIXユーティリティの1つであると考えられており、特にシステム内の他のプログラムと組み合わされたとき、その威力を発揮します。

この記事は、この小さなプログラムの使い方の基本を教えることを目的としています。さらに、UNIX の哲学の簡単な概要と、この哲学がコンピュータの動作を理解する上でいかに重要であるかということも説明します。

UNIX の理念とは何か?

UNIX の哲学とは、プログラムは単一のタスクだけをうまくこなすべきだ という考え方です。他の作業に再利用できないような複雑なプログラムを作るのではなく、異なる機能に再利用できるような単純なプログラムを書くことを推奨しています。

この良い例が cat というプログラムです。これは、入力を受け取り、それをテキストのストリームとして表示するだけの簡単なユーティリティです。

UNIXの哲学は、システム内の他のユーティリティと組み合わせてプログラムを使用することを可能にします。その結果、このアプローチは最終的に、一度学べば異なる文脈でも再利用できる、システム用の単一のインターフェースを作り出します。

例えば、grepのようなプログラムにcatストリームを送り込むことができます。これは単純なプログラムで、たった一つのことしかしない。入力から文字列を探し、その文字列が現れている行を表示します。

一方、同じcatストリームを less のようなスクリーンページャーに送り込むこともできます。これにより、あたかも1つのテキストファイルであるかのように、ストリームをスクロールすることができるようになります。

Sed はどのように動くのか?

とはいえ、sed はテキストのストリームを読み、それを修正するプログラムです。しかし、sed はテキストストリームを変更するだけであり、コンピュータ内のファイルを 直接変更することはありません。これは、sed で行った変更がディスクに表示されないため、初心者にとっては混乱することでしょう。

それにもかかわらず、sed は依然として強力なユーティリティです。例えば、次の行を実行すると、 printf コマンドの出力を読むことができます。

printf "hello ↵↵↵↵↵↵". | sed n

Sed の使い方の基本

これを知っていれば、sed を使って基本的な作業をするのは驚くほど簡単です。次のような例を考えてみましょう。

sed -n p hello.txt

この中で、nコマンドを使って、ファイル「hello」の中身を表示しています。

1. テキストストリームの選択とトリミング

さらに、このテキストのストリームを変更するようにsedに指示することもできます。たとえば、 2q コマンドを使用して、 “hello” ファイルの最初の 2 行だけを表示するように指示することができます。

sed 2q hello.txt

これは、テキストファイルの最初の数行だけを取得したい場合に、非常に便利です。しかし、 p コマンドを使用して、ファイルの中のある範囲の行だけを表示するように sed に指示することもできます。

sed -n 3,4p hello.txt

上の例では、sed を使って “hello” ファイルの 3 行目と 4 行目を表示しました。また、同じ p コマンドを使って、テキストファイルの隣り合っていない行を表示することもできます。次のような例を考えてみましょう。

sed -n 1~4p hello.txt

これで、「hello」ファイルの1行目と4行目だけを表示するようにsedに指示しています。これは、異なるストリームからの複数の行を一つのファイルにまとめたい場合に便利です。

たとえば、sed と > 演算子を使用して、変更されたストリームをファイルに書き出すことができます。

sed -n 1~4p hello.txt > welcome.txt

2. テキストの削除

sedのもう一つの素晴らしい機能は、ストリーム中のテキストを削除することです。印刷とは異なり、sed がストリームから削除したいテキストの行を選択することができます。

たとえば、私は d コマンドを使用して hello ファイルの 2 行目と 5 行目を削除しました。

sed 2~5d hello.txt

p`コマンドの代わりにこれを使う利点の一つは、不要な行だけを削除できることです。これは、大きなファイルを整理したり、必要な情報のみを表示するために出力を切り詰めたりしたい場合に便利です。

3. 新しいテキストを追加する

新しいデータをテキストストリームに含めるために、sed をそれ自体で使用することもできます。たとえば、 a コマンドを使用して、現在のストリームにテキスト行を追加することができます。

sed -n 2p hello.txt | sed a\ "this is a new line".

さらに、ファイル全体をテキストストリームに含めることも可能です。これを行うには、 r コマンドを使用します。このコマンドを使用すると、1つのファイルを現在のストリームに読み込むことができます。これを行うには、次のコマンドを実行して、hello の 2 行目の後に welcome ファイルを含めます。

sed -n 2p hello.txt | sed rwelcome.txt

4. テキストの置換とストリームの操作

sedの輝かしい使い方の1つは、既存のストリームを変更することです。これは、テキスト入力ストリームを受け取り、そのストリームの内容を変更するために sed の組み込み関数を使用する場合です。

これは間違いなく sed の最も強力な機能です。この機能により、パイプを通過するデータを動的に編集することができるようになります。例えば、あるプログラムの出力をテキストファイルのように簡単に編集することができます。

printf "hello 103". | sed s/world/website/

この例では、sコマンドを使って、“world “という単語を “website “に置き換えています。しかし、これまでのコマンドとは異なり、このコマンドは正しく動作させるために特定の構文を使用します。

それを知っていると、sコマンドの一般的な形式は次のようになります。

s/[正規表現]/(文字列)/{options} となります。

5. 5. ファイルでテキスト置換を使う

s` コマンドを使えば、どんな種類のテキストストリームでも操作することができます。これはデータをその場で修正できるだけでなく、Linuxのコマンドラインではほとんど全てのものに使えるので便利です。

例えば、コマンドの最後にファイル名を追加することで、テキストファイルに対して s コマンドを使用することができます。

sed s/hello/welcome/ hello.txt

この例では、sed に “hello” ファイルを読み込んで、最初の “hello” という単語のインスタンスを “welcome” に置き換えるように指示しています。g` オプションを追加することで、ファイル中の “hello” という単語のすべてのインスタンスに対してこの処理を行うことができます。

sed s/hello/welcome/g hello.txt

Frequently Asked Questions (よくある質問)

sed を使ってファイルに変更を書き込むことは可能ですか?

はい! ファイル演算子を使う以外に、sed を使って変更したテキストストリームをファイルに直接書き込むことができます。これを行うには、sed に -i フラグを付けるか、 w コマンドを使用してストリームをファイルに書き込みます。

しかし、注意すべき重要な点は、これらのコマンドは POSIX 標準に準拠していないことです。つまり、GNU 以外のバージョンの sed を使っている場合は、これらは動作しません。

sed を使うたびに “unterminated” エラーになります。私のインストールは壊れているのでしょうか?

いいえ、そんなことはありません。これは、sed コマンドを適切に記述しなかったときに起こる問題です。これは、文字列を空白でマッチさせるか置換するような置換コマンドでよく起こります。

たとえば、次のようなコマンドを実行すると、“unterminated” エラーになります: sed s/hello/welcome back/g hello.txt.

これを解決するには、スペースの前に “absolute “というエスケープキャラクタを追加します。これは、検索や置換の際にスペースを含めるようにsedに指示する特別な文字です。

これで、上記のコマンドの正しいバージョンは次のようになります。sed s/hello/welcome\ back/g hello.txt.

g” 以外に “s” コマンドで使用できるフラグはありますか?

はい、あります。g以外に、p` フラグを使って、変更された行を表示させることができます。

sと一緒に使えるもうひとつのフラグはeです。これは、sed が単語を置き換えるたびにシェルコマンドを実行するようにします。例えば、以下のコマンドを実行すると、ファイルの中に "hello" という単語を見つけるたびにtouch を実行することができます。sed s/hello /touch} /e hello.txt`.

最後に、i フラグを使って、sed がマッチを探すときに大文字と小文字を区別しないようにすることもできます。これは、同じ単語で異なる大文字小文字を区別してマッチさせたい場合に便利です。たとえば、次のコマンドは “hello” という単語を大文字小文字に関係なく “welcome” に置き換えます。sed s/HELLO/welcome/i hello.txt.

この話を聞いて、Linuxのコマンドラインに興味がわきましたか?以前の記事で、今日使える最も面白いBashプロンプトをいくつか紹介していますので、そちらもご覧ください。

画像引用元:Unsplash

Akira
Akiraは情熱的なゲーマーであり、製品レビュアーです。ゲームをしていないときは、最新のゲーミングアクセサリーを試したり、製品のレビューをしていることが多い。彼の分かりやすいスタイルは、ゲーマーが自分のニーズに最も適した製品を簡単に判断できるようにするものです。また、技術的な問題にも精通しており、その解決方法も知っている。