2016-03-22 17 views
1

good discussionsはすでにregular expressions and empty linesになっています。この質問が重複している場合は削除します。正規表現の空白行と空白行の違い

誰でもこのスクリプトが4 3 4 4 4 3の代わりに5 3 4 5 4 3を出力する理由を説明できますか?私がデバッガでそれを実行すると、$blank$classyblankは、print文の直前まで "4"(正しい値であると仮定します)のままです。

my ($blank, $nonblank, $non_nonblank, 
    $classyblank, $classyspace, $blanketyblank) = 0 ; 

while (<DATA>) { 

    $blank++ if /\p{IsBlank}/   ; # POSIXly blank - 4? 
    $nonblank++ if /^\P{IsBlank}$/ ; # POSIXly non-blank - 3 
    $non_nonblank++ if not /\S/  ; # perlishly not non-blank - 4 
    $classyblank++ if /[[:blank:]]/ ; # older(?) charclass blankness - 4? 
    $classyspace++ if /^[[:space:]]$/ ; # older(?) charclass whitespace - 4 
    $blanketyblank++ if /^$/   ; # perlishly *really empty* - 3 

} 

print join " ", $blank, $nonblank, $non_nonblank, 
      $classyblank, $classyspace, $blanketyblank , "\n" ; 

__DATA__ 

line above only has a linefeed this one is not blank because: words 

this line is followed by a line with white space (you may need to add it) 

then another blank line following this one 

THE END :-\ 

はそれ __DATA__セクションとは何かや、私はPOSIX正規表現を誤解していますか?


PS:タイムリーポストelsewhereにコメントで述べたように

、 "本当に空"(/^$/)非空虚を欠場することができます

perl -E 'my $string = "\n" . "foo\n\n" ; say "empty" if $string =~ /^$/ ;' 
perl -E 'my $string = "\n" . "bar\n\n" ; say "empty" if $string =~ /\A\z/ ;' 
perl -E 'my $string = "\n" . "baz\n\n" ; say "empty" if $string =~ /\S/ ;' 
+0

これは、if/\ A \ Z/'と' if/\ A \ z/'...ですが、Python以外の言語ではかなり一貫していますが、それは問題ありません。(http://stackoverflow.com/質問/ 7063420/perl-compatible-regular-expression-pcre-in-python)を使用しています。 –

+0

'これはamd64-freebsd'のために作られたperl 5、version 22、subversion 0(v5.22.0)です –

+1

あなたの中心的な質問には関係ありませんが、' my $ string = "\ n"、 "foo \ n \ n" ' '$ string'に一つの改行を割り当てます。残りはカンマ演算子のために破棄されます。 – ThisSuitIsBlackNot

答えて

2

/\p{IsBlank}/はチェックしません空の文字列の場合\pは、指定されたUnicodeプロパティを持つ文字と一致します。

$ unichars '\p{IsBlank}' | cat 
---- U+0009 CHARACTER TABULATION 
---- U+0020 SPACE 
---- U+00A0 NO-BREAK SPACE 
---- U+1680 OGHAM SPACE MARK 
---- U+2000 EN QUAD 
---- U+2001 EM QUAD 
---- U+2002 EN SPACE 
---- U+2003 EM SPACE 
---- U+2004 THREE-PER-EM SPACE 
---- U+2005 FOUR-PER-EM SPACE 
---- U+2006 SIX-PER-EM SPACE 
---- U+2007 FIGURE SPACE 
---- U+2008 PUNCTUATION SPACE 
---- U+2009 THIN SPACE 
---- U+200A HAIR SPACE 
---- U+202F NARROW NO-BREAK SPACE 
---- U+205F MEDIUM MATHEMATICAL SPACE 
---- U+3000 IDEOGRAPHIC SPACE 

SPACEがISBLANK性を有しているので、それは" \n"に一致します。


/[[:blank:]]/空の文字列をチェックしません。 [...]は、指定したクラスのメンバーである文字と一致します。

$ unichars '[[:blank:]]' | cat 
---- U+0009 CHARACTER TABULATION 
---- U+0020 SPACE 
---- U+00A0 NO-BREAK SPACE 
---- U+1680 OGHAM SPACE MARK 
---- U+2000 EN QUAD 
---- U+2001 EM QUAD 
---- U+2002 EN SPACE 
---- U+2003 EM SPACE 
---- U+2004 THREE-PER-EM SPACE 
---- U+2005 FOUR-PER-EM SPACE 
---- U+2006 SIX-PER-EM SPACE 
---- U+2007 FIGURE SPACE 
---- U+2008 PUNCTUATION SPACE 
---- U+2009 THIN SPACE 
---- U+200A HAIR SPACE 
---- U+202F NARROW NO-BREAK SPACE 
---- U+205F MEDIUM MATHEMATICAL SPACE 
---- U+3000 IDEOGRAPHIC SPACE 

SPACEは、このように[:blank:] POSIX文字クラスのメンバーと[[:blank:]]文字クラスのメンバーであるので、それは" \n"一致しました。

+0

ありがとう、grokに始まる... $ unblank ++ if/\ P {IsBlank}/'(アンカーなし)は私に" 8 "を与えます(' __DATA__'は8行を持っています) '\ n'を非 '{IsBlank}'( '\ P'のため)であり、したがって8つのマッチが見られます。次に、 '/^\ P {IsBlank} $ /'として、3行の空白ではない水平の文字( '\ n')の3行に基づいてインクリメントします。しかし、 '/ \ p {IsBlank}'は、 '\ s'スタイルの水平"空白文字 "を持つ行が5つあるので私に" 5 "のカウントを与えます:4つはテキスト(そして単語間の空白) '' \ n''が空行として表示されます。 –

関連する問題