以前に生成された変数セットを使用して、a.ped_snps.tempというファイルの列をフィルタリングし、bash forループでawkを使用したいと思います。
このために、bash変数を作成しました:var_i_1、var_i_2、... var_i_n_blocksは下限として、var_f_1、var_f_2、... var_f_n_blocksは上限として使用されます。
前述のn_blocksは、var_i_1とvar_f_1などで区切られた列を使用して生成されるファイルの数です。次のスクリプトを使用しました。
n_blocks=$(wc -l "a.temp" | awk '{print $1}') # number of blocks to be created, a.temp is the file with the number of blocks
for i in $(seq 1 1 $n_blocks) # to iterate of first to n_blocks
do
awk -v v_i="$var_i_$i" -v v_f="$var_f_$i" '{ # to declare variables of lower ($var_i_$i) and upper ($var_f_$i) bounds for each iteraction to awk command
for (i=v_i;i<=v_f;i++) {printf (i==1?"":FS)$i}; print "" # for statement to print all comlumns between specified in v_i and v_f variables in each iteraction
}' <a.ped_snps.temp > block_$i.txt # print one txt file with each block for each iteraction
done
このコードは実行され、for コマンドで指定された正しい反復回数でファイルを提供しますが、各ファイルの最初の列のみが出力に出力されます。
awk(下)とvar_i_1およびvar_f_1 bash変数(以前にそれぞれ保存された値2と4を含む)のみを使用すると、出力(block_1.txt)には必須列$ 2、$ 3、および$ 4などが含まれます。他のブロック。
awk -v v_i="$var_i_1" -v v_f="$var_f_1" '{ # declare variables of lower ($var_i_1) and upper ($var_f_1) bounds for first block (set of cloumns)
for (i=v_i;i<=v_f;i++) {printf (i==1?"":FS)$i}; print "" # for statement to print only comlumns between specified in v_i and v_f variables for first block
}' <a.ped_snps.temp > block_1.txt # print one txt file only with a set of columns specified in v_i and v_f variables
それでは、このコードをbashで実装するのに役立つ人がいますか?とにかく、以前にbashのawkコマンドで生成されたbash変数を使用したいと思います。
私の説明が明確であることを願っています。
よろしくお願いします。
答え1
$var_i_$i
値などに拡張する$var_i_1
と予想しているようですが、$var_i_2
残念ながらそうではありません。これを説明するために、次のように設定するとします。
$ var_i_1=23; var_i_2=45; var_i_3=67
それから
$ for i in $(seq 1 3); do awk -v v_i="$var_i_$i" 'BEGIN{print v_i}'; done
1
2
3
ここで起こるのは、シェルが$var_i_$i
次のように解決されることです。$var_i_
関連 $i
。$var_i_
これは設定されていないか、nullになり、v_i
単にv_f
ループインデックス値を継承できるためですi
。
欲しいものを間接的に達成するいくつかの醜い方法があります。
$ for i in $(seq 1 3); do awk -v v_i="$(eval echo \${var_i_$i})" 'BEGIN{print v_i}'; done
23
45
67
しかし、bashは配列をサポートしているので、よりきれいな解決策は配列をvar_i
合計var_f
値として使用することです。
$ var_i=(23 45 67)
それから(配列はゼロインデックスであることを覚えておいてください)
$ for i in $(seq 0 2); do awk -v v_i="${var_i[i]}" 'BEGIN{print v_i}'; done
23
45
67