以下のような感じで、エンコードしないとマッチしない。
use strict; use warnings; use utf8; use Encode; binmode STDOUT, ":utf8"; my $text = "テストhttp://example.com/テスト"; my $regex = q{\b(?:https?|shttp)://(?:(?:[-_.!~*'()a-zA-Z0-9;:&=+$,]|%[0-9A-Fa-f} . q{][0-9A-Fa-f])*@)?(?:(?:[a-zA-Z0-9](?:[-a-zA-Z0-9]*[a-zA-Z0-9])?\.)} . q{*[a-zA-Z](?:[-a-zA-Z0-9]*[a-zA-Z0-9])?\.?|[0-9]+\.[0-9]+\.[0-9]+\.} . q{[0-9]+)(?::[0-9]*)?(?:/(?:[-_.!~*'()a-zA-Z0-9:@&=+$,]|%[0-9A-Fa-f]} . q{[0-9A-Fa-f])*(?:;(?:[-_.!~*'()a-zA-Z0-9:@&=+$,]|%[0-9A-Fa-f][0-9A-} . q{Fa-f])*)*(?:/(?:[-_.!~*'()a-zA-Z0-9:@&=+$,]|%[0-9A-Fa-f][0-9A-Fa-f} . q{])*(?:;(?:[-_.!~*'()a-zA-Z0-9:@&=+$,]|%[0-9A-Fa-f][0-9A-Fa-f])*)*)} . q{*)?(?:\?(?:[-_.!~*'()a-zA-Z0-9;/?:@&=+$,]|%[0-9A-Fa-f][0-9A-Fa-f])} . q{*)?(?:#(?:[-_.!~*'()a-zA-Z0-9;/?:@&=+$,]|%[0-9A-Fa-f][0-9A-Fa-f])*} . q{)?}; # マッチしない if ($text =~ /($regex)/) { print "マッチしない\n"; } # マッチする $text = encode_utf8($text); if ($text =~ /($regex)/) { print $1 . "\n"; print "マッチする\n"; }
とか、書いているうちにRegexp::Commonの存在を思い出した。
これを使えば普通にマッチした。
use strict; use warnings; use utf8; use Regexp::Common qw/URI/; binmode STDOUT, ":utf8"; my $text = 'テストhttp://example.com/テスト'; if ($text =~ /($RE{URI}{HTTP})/) { print "マッチする" . "\n"; }