AWKスクリプトを実行すると構文エラーが発生します。

AWKスクリプトを実行すると構文エラーが発生します。

名前を含むテキストファイルで、ローマ字で表記された韓国語の名前を見つけて、一致する種類の数を確認してから数を印刷しようとしています。これを行うためにAWKスクリプトを作成しましたが、このスクリプトを実行すると、正規表現変数とその周辺の2番目のブロックで構文エラーが発生します'{' '}'。正規表現変数は私の正規表現パターンを保持します。

これは私のコードです。

BEGIN { 
    correctMatch = 0; 
    falsePositive = 0; 
    falseNegative = 0; 
    correctNonMatch = 0;  
    regex = (g|kk|n|d|tt|r|m|b|pp|s|ss|j|jj|ch|tch|k|t|p|h)?(a|ae|ya|yae|eo|e|yeo|ye|o|wa|wae|oe|yo|u|wo|we|wi|yu|eu|ui|i|oo|ah)(k|n|t|l|m|p|ng)? (g|kk|n|d|tt|r|m|b|pp|s|ss|j|jj|ch|tch|k|t|p|h)?(a|ae|ya|yae|eo|e|yeo|ye|o|wa|wae|oe|yo|u|wo|we|wi|yu|eu|ui|i|oo|ah)(k|n|t|l|m|p|ng)?-?(g|kk|n|d|tt|r|m|b|pp|s|ss|j|jj|ch|tch|k|t|p|h)?(a|ae|ya|yae|eo|e|yeo|ye|o|wa|wae|oe|yo|u|wo|we|wi|yu|eu|ui|i|oo|ah)(k|n|t|l|m|p|ng)?;
}

    {
        $NF=="Korean" && tolower($0)~regex {correctMatch = correctMatch + 1}
        $NF!="Korean" && tolower($0)~regex {falsePositive = falsePositive + 1}
        $NF=="Korean" && tolower($0)!~regex {falseNegative = falseNegative + 1}
        $NF!="Korean" && tolower($0)!~regex {correctNonMatch = correctNonMatch + 1}
    }

END {
    print "Correct Match:" correctMatch;
    print "False Positive:" falsePositive;
    print "False Negative:" falseNegative;
    print "Non Correct-Match:" correctNonMatch;
}

ベストアンサー1

{...}コメントですでに述べたように、Cプログラムと同様に、awkジョブセクション内のジョブの前(つまり間)に条件を追加することはできません。この問題を解決し、他の非効率性と不要なコードの重複を解決するには、次のように変更してください。

BEGIN {  
    regex = "(g|kk|n|d|tt|r|m|b|pp|s|ss|j|jj|ch|tch|k|t|p|h)?(a|ae|ya|yae|eo|e|yeo|ye|o|wa|wae|oe|yo|u|wo|we|wi|yu|eu|ui|i|oo|ah)(k|n|t|l|m|p|ng)? (g|kk|n|d|tt|r|m|b|pp|s|ss|j|jj|ch|tch|k|t|p|h)?(a|ae|ya|yae|eo|e|yeo|ye|o|wa|wae|oe|yo|u|wo|we|wi|yu|eu|ui|i|oo|ah)(k|n|t|l|m|p|ng)?-?(g|kk|n|d|tt|r|m|b|pp|s|ss|j|jj|ch|tch|k|t|p|h)?(a|ae|ya|yae|eo|e|yeo|ye|o|wa|wae|oe|yo|u|wo|we|wi|yu|eu|ui|i|oo|ah)(k|n|t|l|m|p|ng)?"
}
{
    hitNf = ( $NF == "Korean" )
    hitRe = ( tolower($0) ~ regex )
    correctMatch   += (  hitNf &&  hitRe )
    falsePositive  += ( !hitNf &&  hitRe )
    falseNegative  += (  hitNf && !hitRe )
    correcNonMatch += ( !hitNf && !hitRe )
}
END {
    print "Correct Match:" correctMatch+0
    print "False Positive:" falsePositive+0
    print "False Negative:" falseNegative+0
    print "Non Correct-Match:" correctNonMatch+0
}

上記の構造を使用すると、最初に変数に保存するのではなく、正規表現を直接テストできます。ただし、コードはregex = foo正規表現を変数に保存しませんregex。上記でこの問題を修正しましたがregex = "foo"(動的正規表現)、最新バージョンのGNU awkもそれをサポートしていますregex = @/foo/https://www.gnu.org/software/gawk/manual/gawk.html#Compulated-Regexpsそしてhttps://www.gnu.org/software/gawk/manual/gawk.html#Regexp-Constants

おすすめ記事