grep

基本的な機能は、文字列を検索することです。基本的な使い方は、

grep 文字列 ファイル名

と打ち込んでリターンすると、指定したファイルの中で、文字列が存在する行の 中身が表示されます。

それでは実習のために、下記のような内容のファイル「address1.txt」と 「address2.txt」を作ってみましょう。

% emacs address1.txt

と実行して、emacs上で下記の内容を打ち込んでください。「address2.txt」に 関しても同様の手順でやってみてください。ちなみに、前者はリテラシーの 先生方のメールアドレス、後者は自分の友人のメールアドレスという位置づけです。

% cat address1.txt
suzuki@zzz.tuis.ac.jp
doi@zzz.TUIS.AC.JP
susaki@aaa.bb.cc.dd
ohshiro@yahoo.co.jp
yamaga@yyy.com
sinohara@joho.ac.jp


% cat address2.txt
e02000ab@zzz.tuis.ac.jp
endo@chiba-u.ac.jp
e01050hh@zzz.tuis.ac.jp
s02000ab@zzz.tuis.ac.jp
m02134yn@zzz.tuis.ac.jp
b99055cc@yyy.tuis.ac.jp
c99123ym@zzz.tuis.ac.jp
a00106sn@zzz.tuis.ac.jp

この2つのファイル「address1.txt」「address2.txt」を元に、grepの使い方を 学習していきます。

  1. まずはgrepの基本型を学びましょう。「address1.txt」のうち、「suzuki」とい う文字列が含まれている行を表示させましょう。下記のように実行してみましょ う。
    % grep suzuki address1.txt
    suzuki@zzz.tuis.ac.jp
    
    と表示されるはずです。行番号をつけたい場合には、
    % grep -n suzuki address1.txt
    1:suzuki@zzz.tuis.ac.jp
    
    のように「-n」オプションをつけます。 Number(数字)と覚えましょう。
  2. 次に、「address1.txt」のうち、「tuis」という文字列が含まれている行を 表示させましょう。下記のように実行してみましょう。
    % grep tuis address1.txt
    suzuki@zzz.tuis.ac.jp
    
    のような結果になりました。2行めには「doi@zzz.TUIS.AC.JP」とありますが、 基本的には大文字と小文字が区別されているのがわかりました。大文字、小文字 に関係なく「tuis」という文字列が含まれている行を表示させるには、
    % grep -i tuis address1.txt
    suzuki@zzz.tuis.ac.jp
    doi@zzz.TUIS.AC.JP
    
    と、「-i」オプションをつけます。 Ignore(無視する)と覚えましょう。
  3. では、「address1.txt」のうち、「zzz」という文字列が含まれている行の数を 知りたい場合があります。その場合は、下記のように実行してみましょう。
    % grep -i -c zzz address1.txt
    (または)
    % grep -ic zzz address1.txt
    2
    
    と、「-c」オプションをつけます。 Count(数える)と覚えましょう。
  4. 余談ですが、今までは指定した文字列が含まれる行を表示させてきましたが、逆 に含まれない行を表示させるには、 「-v」オプションをつけます。
    % grep -v zzz address1.txt
    doi@zzz.TUIS.AC.JP
    susaki@aaa.bb.cc.dd
    ohshiro@yahoo.co.jp
    yamaga@yyy.com
    sinohara@joho.ac.jp
    
    % grep -iv zzz address1.txt
    susaki@aaa.bb.cc.dd
    ohshiro@yahoo.co.jp
    yamaga@yyy.com
    sinohara@joho.ac.jp
    

    練習問題:
  1. 「address2.txt」に対して、「zzz.tuis.ac.jp」ドメインのメールアドレスだけ を表示させよ。
    (実行結果)
    e02000ab@zzz.tuis.ac.jp
    e01050hh@zzz.tuis.ac.jp
    s02000ab@zzz.tuis.ac.jp
    m02134yn@zzz.tuis.ac.jp
    c99123ym@zzz.tuis.ac.jp
    a00106sn@zzz.tuis.ac.jp
    
  2. 「address2.txt」に対して、「zzz.tuis.ac.jp」ドメインのメールアドレスは いくつあるか?
    (実行結果)
    6
    
  3. 「address2.txt」に対して、「tuis.ac.jp」ドメインでないメールアドレスは いくつあるか?
    (実行結果)
    1
    

  1. それでは少し複雑な処理を行いましょう。「address1.txt」のうち、「ac.jp」 または「co.jp」という文字列が含まれている行 を表示させたい場合があります。その場合は、
    % grep  -e  ac.jp  -e co.jp  address1.txt
    suzuki@zzz.tuis.ac.jp
    ohshiro@yahoo.co.jp
    sinohara@joho.ac.jp
    
    のように、「-e」オプションをつけて複数の文 字列を指定します。もし「-e」オプションをつけずに複数の文字列を指定すると、
    % grep  -e  ac.jp  co.jp  address1.txt
    grep: co.jp: そのようなファイルやディレクトリはありません
    address1.txt:suzuki@zzz.tuis.ac.jp
    address1.txt:sinohara@joho.ac.jp
    
    と、「co.jp」も「address1.txt」もファイルとして扱われ、「co.jp」というファ イルのうち、「ac.jp」という文字列を探そうとします。実際には「co.jp」とい うファイルはありませんので、上記のようなエラーメッセージが表示されます。
  2. 今度は、「address1.txt」のうち、「ac.jp」 かつ「sinohara」という文字列が含まれている行 を表示させるとします。その場合は、
    % grep  -e  ac.jp  address1.txt | grep  sinohara
    sinohara@joho.ac.jp
    
    のように、オプションではなく、「| (パイプ) 」を利用します。これは
    % grep  -e  ac.jp  address1.txt
    suzuki@zzz.tuis.ac.jp
    sinohara@joho.ac.jp
    
    と表示されているように、「ac.jp」を含む行「suzuki@zzz.tuis.ac.jp」 「sinohara@joho.ac.jp」に対して、さらに「sinohara」という 文字列を探し、含まれる行だけを表示させます。2段階で処理をしていると理解 して下さい。
  3. ここで、複雑な処理が実現するための正規表現記号 を使う練習をしましょう。要は、*, ^ $などの記号を使って、 細かい条件を設定できるということです。このような記号は、文字を一般化して 表す文字と考えられ、メタ文字と呼ばれていま す。このメタ文字を使った検索例(以下では、「マッチ」という言葉を使ってい ます)を下記に示します。

    メタ文字 マッチングの条件 用例 マッチング例
    ^ 行の先頭にあればマッチする ^and ando
    anddddddd
    $ 行のおわりにあればマッチする and$ land
    dreamland
    . 任意の1文字が存在すればマッチ fa. fax
    fantastic
    * 直前のものが0回以上繰り返すとマッチ yahoo* yaho
    yahooooo
    [...] [ ]内の任意の一文字にマッチ data[0123456789]
    data[0-9]
    注意:2つとも同じ意味
    data1
    data8
    data[abcde]
    data[a-e]
    注意:2つとも同じ意味
    dataa
    datac
    data[a-zA-Z0-9_] data1
    dataB
    [^ ] 否定 data[^0-5] data7
    datac
    data[^abc] data7
    datad
    ^[^abc]
    注意:行先頭が'a','b','c'
    以外で始まる場合にマッチ)
    yzaw
    eeeeee

    上記のメタ文字のうち、 * [ [ ]を使って検索する 文字列を指定する場合は、 " "でくくると覚えておきましょう。

    それでは、メタ文字を使った検索を試してみましょう。まずは下記のように実行 してみてください。
    % grep  o address1.txt
    doi@ZZZ.TUIS.AC.JP
    ohshiro@yahoo.co.jp
    yamaga@yyy.com
    sinohara@joho.ac.jp
    
    oという文字が含まれる行を表示してくれます。ここで、 先頭がoで始まる行だけを表示させたいとします。この ような場合にメタ文字を使うのです。
    % grep  ^o address1.txt
    ohshiro@yahoo.co.jp
    
    と望み通りの結果が表示されました。

    今度は下記のように実行してみてください。どういう検索条件でしょうか?
    % grep "^.[aiueo]" address1.txt
    suzuki@zzz.tuis.ac.jp
    doi@ZZZ.TUIS.AC.JP
    susaki@aaa.bb.cc.dd
    yamaga@yyy.com
    sinohara@joho.ac.jp
    
    上記の検索は、「行頭は任意の1文字、その次の文字は'aiueo'のどれか1文字」 である行だけを表示させる命令です。

    練習問題:
    address2.txtの中身
    e02000ab@zzz.tuis.ac.jp
    endo@chiba-u.ac.jp
    e01050hh@zzz.tuis.ac.jp
    s02000ab@zzz.tuis.ac.jp
    m02134yn@zzz.tuis.ac.jp
    b99055cc@yyy.tuis.ac.jp
    c99123ym@zzz.tuis.ac.jp
    a00106sn@zzz.tuis.ac.jp
    
  1. 「address2.txt」に対して、環境情報学科の学生のメールアドレスだけ を表示させよ。
    ヒント:環境情報学科の学生のメールアドレスは「e」で始まり、 そのあと数字が続くことに着目
    (実行結果)
    e02000ab@zzz.tuis.ac.jp
    e01050hh@zzz.tuis.ac.jp
    
  2. 「address2.txt」に対して、環境情報学科の学生、および情報学科の学生の メールアドレスだけを表示させよ。
    ヒント:情報学科の学生のメールアドレスは「b」で始まり、 そのあと数字が続くことに着目
    (実行結果)
    e02000ab@zzz.tuis.ac.jp
    e01050hh@zzz.tuis.ac.jp
    b99055cc@yyy.tuis.ac.jp
    
  3. 「address2.txt」に対して、2000年および2001年入学の学生の メールアドレスだけを表示させよ。
    ヒント:メールアドレスの先頭から2番目、3番目の数字が「00」または「01」で あることに着目
    (実行結果)
    e01050hh@zzz.tuis.ac.jp
    a00106sn@zzz.tuis.ac.jp
    
  4. 「address2.txt」に対して、ユーザID(@より前の部分)が文字だけで 構成されるメールアドレスだけを表示させよ。
    (実行結果)
    endo@chiba-u.ac.jp
    

[UNIXコマンドのページ] [須崎純一のトップページ]
須崎純一 京都大学大学 工学研究科都市環境工学専攻 環境情報学講座