やっと,最終章にたどりつきましたよ.最後はevalの使い方,map,grep,あと,スライシングなどがテーマ.
1. 単語のリストをファイルから読み込み,ユーザが入力した正規表現をマッチさせ結果を表示する
以外に単純そうな問題ですが,これを今までの知識を工夫してうまく書いてみよう,という趣旨だと思う.
適当な入力ファイルがないんですが,とりあえず以下のを使いました.
haruhi mikuru yuki yuki haruhi kyon haruhi mikuru
ちょっと単純すぎる気もするがまぁいいや.
このファイルを配列に読み込んで,一つずつマッチさせる感じですね.マッチした単語を抜き出すのにはgrepを使います.さらに,入力された正規表現のエラー処理にevalを使用.以下にコード.
#!/usr/bin/env perl -w use strict; # 入力ファイルの指定 my $infile = 'words.txt'; open IN, $infile or die "cannot open $infile: $!"; # リストコンテキストで一気に読み込む chomp(my @words = <IN>); close IN; while (1) { # 空行の入力があるまで # 正規表現の入力を受け付ける print "input your regext: "; chomp(my $regex = <STDIN>); last if $regex =~ /^\s*$/; # 空行ならループをぬける my @matches; eval { # evalでエラーをキャッチ # grep を使ってマッチした単語を抜き出す @matches = grep /$regex/, @words; }; if ($@) { # エラーが起きた時 print "error occured: $@"; next; } # 結果を表示 my $count = $#matches + 1; print "$count matches: \n"; for my $word (@matches) { print "$word\n"; } print '-'x10,"\n"; } print "done\n";
さて,さて,実行してみますよ.
$ ./ex17.pl input you regext: haruhi # 普通の文字列で 3 matches: haruhi haruhi haruhi ---------- input you regext: ^[hy] # 当然正規表現つかえます 5 matches: haruhi yuki yuki haruhi haruhi ---------- input you regext: (mikuru # 正規表現に問題があると error occured: Unmatched ( in regex; marked by <-- HERE in m/( <-- HERE mikuru/ at ./ex17.pl line 23, <STDIN> line 3. input you regext: done
はい,できましたー!.解答では,さらにforのかわりにmapを使ってきれいに出力していました.17章は1問だけであっさり終了ですね.
というわけで,初めてのPerlの練習もんだいついにコンプリート.これ,ちょっとまとめたエントリーを書くかな.