awkで分割すると、配列値は印刷されません。

awkで分割すると、配列値は印刷されません。

以下を含む文字列tstArr2があります。

'3 5 8'

それでは、awkでフラットファイルを解析したいと思います。

test my array which array is better array

INDIA USA SA NZ AUS ARG GER BRA
US AUS INDIA ENG NZ SRI PAK WI BAN NED IRE

この番号が付けられた列にのみ存在します。私は次を試しました

awk -vA="$tstArr2" 'BEGIN{split(A,B," ");} {if(NR>1){for(i=1; i<= length(B); i++){printf "%s ",B[i]}}print " "}' testUnix3.txt

しかし、それは言う

awk: Cannot read the value of  B. It is an array name.

The input line number is 2. The file is testUnix3.txt.
The source line number is 1.

私は何を見逃していますか?以下を試してみると

awk -vA="$tstArr2" 'BEGIN{split(A,B," ");} {if(NR>1){for(i in B){printf "%s ",$B[i]}}print " "}' testUnix3.txt

出力は印刷されますが、順番に印刷されません。私は彼らが順番にいることを願っています。説明してください。希望の出力:

 SA AUS BRA

 INDIA NZ WI

答え1

POSIXの定義長さinは、awkパラメータを文字列として含む文字列関数です。配列を引数として使用することは、指定されていlengthない動作です。

いくつかのawk同様の実装ではgawk (バージョン >= 3.1.6)AWKのOS Xバージョン、配列を引数として使用でき、length配列の要素数を返します。

の配列はawk連想配列であり、連想配列による反復は順序を保証しません。この場合、以下を使用できます。分ける配列の要素数を取得するためにフィールド数を返す関数です。

POSIXlyでは、次のことを試すことができます。

$ awk -vA="$tstArr2" '
  BEGIN{n = split(A,B," ");}
  {
    if(NR > 1) {
      for(i = 1;i <= n;i++) {
        printf "%s ",$B[i];
      }
    }
    print " ";
  }
' file

SA AUS BRA  
INDIA NZ WI

答え2

(GNU以外のawkの場合は@cuonglmの答えを参照してください。)

これをテストファイルとして使用します。

$ cat testUnix3.txt 
test my array which array is better array

INDIA USA SA NZ AUS ARG GER BRA
US AUS INDIA ENG NZ SRI PAK WI BAN NED IRE

このコードは列3、5、8を選択します。

$ tstArr2='3 5 8'
$ awk  -vA="$tstArr2" 'BEGIN{split(A,B," ");} NR>1{for(i=1; i<= length(B); i++) printf "%s ",$B[i]; print "";}' testUnix3.txt

SA AUS BRA 
INDIA NZ WI 

上記はGNUを使用してテストされましたawk

awkループとシーケンス

awk関連配列があります。 〜のようにグレイモア awk チュートリアル 説明する:

特に、連想配列を使用する場合、小さな問題があります。~のため各要素の出力コマンド:出力順序を制御できません。

for(i in B)これは、ループを使用する他の引用符でコードが時々順序が間違った列を印刷する可能性がある理由です。

GNU awkには、この問題を解決するための拡張機能があります。

$ gawk -vA="$tstArr2" 'BEGIN{split(A,B," "); PROCINFO["sorted_in"]="@ind_num_asc"} {if(NR>1){for(i in B){printf "%s ",$B[i]}print " "}}' testUnix3.txt

SA AUS BRA  
INDIA NZ WI  

を設定すると、PROCINFO["sorted_in"]="@ind_num_asc"インデックスは数値の昇順で循環します。この GNU 拡張は文書化されています。ここ

答え3

awkこれらの簡単な作業にこれらの強力なツールを使用するにはかなりのオーバーヘッドがあります。

tstArr2='3,5,8'
tail -n+2 testUnix3.txt | cut -d' ' -f"$tstArr2"

関連情報