正規表現検索の練習

最初に作成した meibo.csv のデータ

ナマエ,Name,氏名,居住地
サトウ ムネユキ,SATOH Muneyuki,さとう胸幸,青葉台
ナカマチ タロウ,NAKAMACHI Taro,中町太郎,酒田
イイモリ ハナコ,IIMORI Hanako,飯森花子,飯森山
サイトウ テツヤ,SAITOH Tetsuya,斎藤徹夜,白夜の国
ゲゲノ キタロウ,GEGENO Kitarou,下々野喜太郎,魔界村
ナニワノ タロー,NANIWANO Taro,浪花之太朗,探偵騎士王国
ヒミ ヨンタロウ,HIMI Yontarou,悲見四太郎,甲子園
ヤマタイ ヒミコ,YAMATAI Himiko,邪馬台氷見子,大和
イモリ テツコ,IMORI Tetsuko,井森徹子,井戸

を利用して、いくつか検索練習してみよう。

利用するプログラムは、さきほどの saito.rb

#!/usr/koeki/bin/ruby
# -*- coding: utf-8 -*-
require 'csv'

meibo = CSV.read(ARGV[0], headers:true)
meibo.each do |row|
  if /sai?toh/i =~ row["Name"]
    print row.to_s
  end
end

だと決まったパターンしか検索できないので以下のように変更しよう。

meibosearch.rb

#!/usr/koeki/bin/ruby
# -*- coding: utf-8 -*-
require 'csv'
meibo = CSV.read(ARGV[0], headers:true)	# ./meibosearch.rb meibo.csv と起動する

print "検索パターン: "
pattern = STDIN.gets.chomp!
regexp = Regexp.new(pattern, nil)

meibo.each do |row|
  line = row.to_s
  if regexp =~ line
    print line
  end
end

プログラム中の、STDIN は標準入力を意味する。 Rubyプログラム起動時にファイルを引数に与えると gets を利用 したときにそのファイルからデータを読む。しかし、STDIN.gets とすると、ファイルを引数に与えたとしても標準入力から1行読む。 これを、chomp!で 改行を切り取り、さらに Regexp.new メソッドに渡して正規表現 にしている。

ひらがなを含む行の検索

ひらがなは正規表現 [ぁ-ん] で表現できる。

./meibosearch.rb meibo.csv
検索パターン: [ぁ-ん]
サトウ ムネユキ,SATOH Muneyuki,さとう胸幸,青葉台
サイトウ テツヤ,SAITOH Tetsuya,斎藤徹夜,白夜の国

ちいさい「ぁ」は la (えるえー)で入力する。

「サ」で始まる人全てを検索

行の先頭は ^ で指定する。^サ とすると 行の先頭が「サ」で始まるもののみにマッチする。

./meibosearch.rb meibo.csv
検索パターン: ^サ
サトウ ムネユキ,SATOH Muneyuki,さとう胸幸,青葉台
サイトウ テツヤ,SAITOH Tetsuya,斎藤徹夜,白夜の国

同じ文字(空白以外)が繰り返す行の検索

グルーピングを使うと繰り返しを記述できる。空白以外の文字は \S である。これを括弧でグルーピングして、\数字 で参照すればよい。正規表現は (\S)\1 となる。

./meibosearch.rb meibo.csv
検索パターン: (\S)\1
イイモリ ハナコ,IIMORI Hanako,飯森花子,飯森山
ゲゲノ キタロウ,GEGENO Kitarou,下々野喜太郎,魔界村

「イ」と「ゲ」が2字連続で出てくるのでこれにマッチする。

下の名前に「ヒミ」が付く人を検索

苗字は行頭なので ^ 記号で絞り込みできるが、 下の名前は行の途中なので絞り込めない。苗字と下の名前の区切りに スペースがあることを利用し、

行頭 + 苗字 + 空白 + 下の名前

というパターンを記述する。苗字は単語だったら何でも構わないので 「1文字以上の非空白文字」を意味する \S+ で マッチングさせる。下の名前は「ヒミ」が最初に来ても最後に来ても 途中に来ても、「ヒミ」全部でもよいようなパターンを指定するので \S*ヒミ\S*\b とする。

./meibosearch.rb meibo.csv
検索パターン: ^\S+\s+\S*ヒミ\S*\b
ヤマタイ ヒミコ,YAMATAI Himiko,邪馬台氷見子,大和

ちなみに「ヒミを含む」という部分のパターンを .*ヒミ.* などとしてしまうと、1つめの.* の部分で空白を越えてマッチする可能性があるため、マッチした「ヒミ」が 必ずしも下の名前の位置にあるとは限らなくなってしまう。

名前が「たろう」の人

名簿を見ると「タロウ」と「タロー」がいるので、「タロ」の 次が「ウ」でも「ー」でもマッチするよう タロ[ウー] とする。ただし名前の途中にそれらが含まれるものは除外したいので 単語境界を意味する\bで絞り込みを行なう。

./meibosearch.rb meibo.csv
検索パターン: \bタロ[ウー]\b
ナカマチ タロウ,NAKAMACHI Taro,中町太郎,酒田
ナニワノ タロー,NANIWANO Taro,浪花之太朗,探偵騎士王国

本日の目次