Your browser doesn't support the features required by impress.js, so you are presented with a simplified version of this presentation.
For the best experience please use the latest Chrome, Safari or Firefox browser.
目標時間 : 20分
perl
が含まれる場合, We love perl!
と表示しよう.END
が入力されるまで, この処理を続けよう.
#!/usr/bin/env perl
use utf8;
use strict;
use warnings;
binmode STDIN, ":encoding(UTF-8)";
binmode STDOUT, ":utf8";
binmode STDERR, ":utf8";
@
をat
に書き換えたい場合を考えます.
my @mails = ('papix2011@gmail.com', 'hogehoge@fugafuga.com');
my @no_spam;
for my $mail (@mails) {
$mail =~ s/\@/ at /;
push @no_spam, $mail;
}
print join("\n", @no_spam);
my @mails = ('papix2011@gmail.com', 'hogehoge@fugafuga.com');
my @no_spam = map{ my $mail = $_; $mail =~ s/\@/ at /; $mail; } @mails;
print join("\n", @no_spam);
my @no_spam = map{ my $mail = $_; $mail =~ s/\@/ at /; $mail; } @mails;
@mails
です.{
と}
で囲った中に, 配列(今回の場合は@mails
)の各要素に対して行いたい処理を書きます.
$_
に格納されます. 但しこれは元の要素へのリファレンスなので, 元の要素を変更したくない場合は, 例のように別の変数に格納する必要があります.@no_spam
です.
my @num = (1, 12, 10, 3, 5, 20, 8, 13, 19, 6);
my @mini;
for my $i (@num) {
push(@mini, $i) if($i <= 10);
}
print join(',', @mini);
my @num = (1, 12, 10, 3, 5, 20, 8, 13, 19, 6);
my @mini = grep { $_ <= 10 } @num;
print join(',', @mini);
my @mini = grep { $_ <= 10 } @num;
@num
です.{
と}
で囲った中に書かれた条件を満たす要素のみで配列を作ります.
@num
)の各要素に対して10以下かどうか($_ <= 10
)をチェックして, これを満たす要素のみを含む配列を作ります.$_
で示されます.@mini
です.is perl monger!
を付け足した配列を返す関数を作ってみよう.papix
の場合, papix is perl monger!
と書き換えられます.yapc
の場合, is perl conference!
を付け足すようにしましょう.
my $str = 'Perl Entrance #7 一緒にPerlを学びましょう!';
print "'$str'は'Perl'を含みます." if $str =~ /Perl/;
$str
の文字列中に, /
で囲まれた正規表現で示される文字列が存在するなら, 「マッチした」と扱われ, 真となります.
my $ans = 'y';
if($ans =~ /[yY]/) {
print "文字列にはyないしYが含まれています.\n";
}
[
と]
で文字をくくると, []の中の任意の1文字にマッチします./[yY]/
は, y
ないしY
にマッチします.
my $ans = 'n';
if($ans =~ /[^yY]/) {
print "文字列にはyないしY以外の文字が含まれています.\n";
}
[
と]
で文字をくくり, その先頭に^
を置くと, []の中にない任意の1文字にマッチします./[^yY]/
は, y
ないしY
以外の文字にマッチします.^
は, 必ず[
の後に置いて, [^
の形で用います.
my $ans = '1';
if($ans =~ /[a-c]/) {
print "文字列にはa, b, cのいずれかが含まれています.\n";
}
[
と]
の中で, 文字の間に-
を挟むことによって, 文字列の範囲を表現できます.[a-c]
は[abc]
と同じ意味になります. [1-5]
のように, 数値に対しても利用できます.
my $ans = 'get';
if($ans =~ /g.t/) {
print "マッチ!\n";
}
.
は, 改行文字(\n
)を除く, 任意の1文字にマッチします./g.t/
は, get
やgot
など, g+任意の1文字+t
にマッチします.
.
がマッチするのは1文字だけなので, goat
などはマッチしません.gt
にもマッチしません.
my $ans = 'gt';
if($ans =~ /g.?t/) {
print "マッチ!\n";
}
?
は, その直前の要素が0個または1個の場合にマッチします.
ab?
は, a
またはab
にマッチします./g.?t/
は, g+任意の1文字+t
に加え, gt
にもマッチします.
my $ans = 'get';
if($ans =~ /g.+t/) {
print "マッチ!\n";
}
+
は, その直前の要素が1個以上の場合マッチします.
ab+c
は, abc
やabbbbc
などにマッチしますが, ac
にはマッチしません./g.+t
は, g+任意の1文字以上+t
にマッチします.
my $ans = 'great';
if($ans =~ /g.*t/) {
print "マッチ!\n";
}
*
は, その直前の要素が0個以上の場合マッチします.
ab*c
は, ac
やabc
, abbbbbc
などにマッチします./g.*t/
は, g
で始まりt
で終わる全てのフレーズとマッチします(great
など).
my $str = 'Gyaaaaaaaaa!';
print "マッチ!\n" if $str =~ /a{5,}/;
# マッチする
my $str2 = 'Gyaa!';
print "マッチ!\n" if $str2 =~ /a{5,}/;
# マッチしない
{m,n}
... その直前の要素がm回以上, n回以下繰り返す場合マッチ{m,}
... その直前の要素がm回以上繰り返す場合マッチ{m}
... その直前の要素がm回繰り返す場合マッチ
my $str = '私は perl が好きです.';
if($str =~ /私は (.+) が好き/) {
print "彼は, $1 が好きです.\n";
# '彼は, perl が好きです'と表示.
}
()
を囲むと, そのパターンに一致する文字列を取得することができます.perl
が入り, 彼は, perl が好きです.
と表示されるはずです.
my $str = '私は perl と 旅行 が好きです.';
if($str =~ /私は (.+) と (.+) が好き/) {
print "彼は, $1 と $2 が好きです.\n";
# '彼は, perl と 旅行 が好きです.'と表示.
}
()
が存在する場合, 先頭から$1
, $2
... で取得することができます.
my $str = 'Hello hoge! Hello fuga!';
if($str ~= /Hello (.+)!/) {
print "Nice to meet you, $1!\n";
}
hoge
を抜き出してNice to meet you, hoge!
としたいので, このようなコードを書きました.Nice to meet you, hoge! Hello fuga!
と表示されます.
my $str = 'Hello hoge! Hello fuga!';
if($str ~= /Hello (.+?)!/) {
print "Nice to meet you, $1!\n";
}
?
を付けて, 最短マッチにすれば, Nice to meet you, hoge!
と出力されるはずです.
while( chomp (my $line = <STDIN>) ) {
print $line;
}
john
が含まれる場合のみ, 文字列を出力しないように書き換えてみよう.
my $str = 'abc def ghi';
$str =~ s/abc/ABC/;
# $str = 'ABC def ghi';
s/PATTERN/REPLACE/
で, PATTERN
をREPLACE
に置換します.s/PATTERN/REPLACE/g
と表記します.
g
を付けることで, 繰り返し評価します.
my $str = 'perl ruby python';
my $pattern = 'perl';
if($str =~ /$pattern/) {
print "'$str'には'$pattern'が含まれます.\n";
}
\w
... アルファベット, 数字, アンダーバーの1文字
[a-zA-Z0-9_]
と同じ意味です.\W
... アルファベット, 数字, アンダーバー以外の1文字
[^a-zA-Z0-9_]
と同じ意味です.\d
... 数字の1文字
[0-9]
と同じ意味です.\D
... 数字以外の1文字
[^0-9]
と同じ意味です.\s
... 空白文字にマッチ
[ \n\r\f\t]
と同じ意味です.\S
... 空白文字以外にマッチ
[^ \n\r\f\t]
と同じ意味です.
my $str1 = '2012年7月22日';
if($str1 =~ /(\d+)年(\d+)月(\d+)日/) {
print "$1/$2/$3";
# "2012/7/22"と表示される.
}
my $str2 = "この 文章 は\n 読みにく\nい で \t す\n";
my $str2 =~ s/\s+//g;
# $str2 = "この文章は読みにくいです";
\s
を使えば, 余分な空白や改行を抜き取ることができます.|
... 選択一致
abc|def|ghi
は, abc
, def
, ghi
のいずれかにマッチします.(x)
... グループ化
()
の中のパターンにマッチした文字列は記憶されます(後方参照).(?:x)
... 後方参照しないグループ化
()
の中のパターンにマッチした文字列は記憶されません.
my $str = 'perl is good!';
if($str =~ /(?:perl|ruby|python) is (good|bad)!/) {
print "評価は $1 です!\n";
# "評価は good です!"と表示される.
}
perl
, ruby
, python
を|
でつなぎ, (
と)
で囲うことで, 選択一致をグループ化しています.(?:
とすることで, 後方参照しないようにしています.
(good|bad)
のパターンにマッチした文字列となります.
my $str = 'john is dead.';
print "john\n" if $str =~ /dead./;
print "john\n" if $str =~ /dead\./;
\
... メタ文字を無効化する
/
や.
など)を無効化します.$str =~ /dead./
は, john is dead!
などでもマッチしてしまう(.
は任意の1文字とマッチ, なので).\.
のようにすれば .
そのものとのマッチができます.john
ないしJohn
が含まれる場合のみ, 文字列を出力しないように書き換えてみよう.^
... 行頭\A
... 最初の文字列
^
と\A
はよく似ていますが, 複数の行がある文字列に正規表現を行った場合, 挙動が異なります.^
は改行の直後(新しい行の行頭)にもマッチしますが, \A
は文字列そのものの先頭にしかマッチしません.$
... 行末\Z
... 最後の文字列
$
は改行の直前にもマッチしますが, \A
は文字列そのものの最後にしかマッチしません.^
と\A
の関係と似ています.
my $str = 'john is great';
# 行頭に'john'がある場合のみマッチ
print "マッチ!\n" if $str =~ /^john/;
# 行末に'great'がある場合のみマッチ
print "マッチ!\n" if $str =~ /great$/;
\b
... 文字の区切り
\b
は, \w
と\W
の間とマッチします.\B
... 文字の区切り以外
my $str = 'lyrical magical';
print "マッチ!\n" if $str =~ /lyrical\b/;
# マッチします.
my $str2 = 'lyricalmagical';
print "マッチ!\n" if $str2 =~ /lyrical\b/;
# マッチしません.
lyricalmagical
は, lyrical
の後に文字の区切りが存在しないので, 2つ目の正規表現はマッチしません.john
, John
を含む.betty
, Betty
を含む.great
, Great
を含む.
my $str = 'john betty beth';
print "マッチ!\n" if $str !~ /beth/;
# 何も表示されない.
!~
演算子は=~
演算子の否定です.beth
を含まない場合, 真となって文字列が出力されます.
my $str = '/usr/local/bin/perl';
print "マッチ!\n" if $str =~ m|bin/perl|;
/
で区切りますが, /
だと不都合な場合も多いです(例えば, URLを表記する場合など. 全ての/
をエスケープする必要がある).m//
のように, 先頭にm
を付けると, 任意の記号のペアを区切り記号として利用することができます.|
を区切り記号にしています. よって, /
をエスケープする必要はありません.
my $str = '/usr/local/bin/perl';
$str =~ s|/usr/local/bin/|/usr/bin/perl|;
//
の後にオプションを与えることができます.
my $str = 'Hello, hoge! Hello, fuga!';
my @name = ($str =~ /Hello, (\w+?)!/);
# @name = ('hoge', 'fuga'); となる.
g
は, 正規表現のマッチングを繰り返し行います.()
が含まれる場合, マッチした文字列のうち()
の中に含まれる文字列をリストとして返します.
my $str = 'Hello, hoge! Hello, fuga!';
my $str =~ s/Hello/Good morning/g;
s///g
とすると, 置換の処理を繰り返し行なってくれます.
my $str = 'John and Beth';
pritn "マッチ!\n" if $str =~ /john/i;
i
は, 正規表現中のアルファベットの大文字・小文字を区別せずにマッチングを行います./john/i
は, john
はもちろん, John
やJOHN
, jOhN
などにもマッチします.john
, John
を含む.betty
, Betty
を含む.great
, Great
を含む.tom
というアルファベットを含む(大文字・小文字問わず).papix
が含まれる場合, 全てhoge
に書き換えてから出力するようにしてみよう.
ジュース:100円
弁当:300円
漫画:400円
カップ麺:250円
お菓子:100円
price.txt
を読み込み, 左側の商品名をキーとして, 右側の価格を値を持つハッシュ%price
を作りましょう.:
で仕切られてるとします.price.txt
の価格を1.05倍(消費税を加算)したテキストを, price+.txt
に書き出すようにしてみましょう.Use a spacebar or arrow keys to navigate