ファイル1には2つの列が含まれています。列1には代謝経路の名前が含まれ、列2には経路に存在する遺伝子の数が含まれています。
pathway1 3
pathway2 4
pathway3 5
pathway4 6
pathway5 9
ファイル2には3つの列があります。列1にはグループ番号が含まれ、列2には特定のグループに属する代謝経路の名前が含まれ、列3には各経路に存在する遺伝子の数が含まれます。
group1 pathway1 2
group1 pathway4 5
group1 pathway2 3
group2 pathway2 1
group2 pathway3 2
ファイル1とファイル2はcsv形式です。
目的の出力:
次のように、パス名に基づいてFile2の列3の横にあるFile1の列2の遺伝子数をどのように印刷できますか?
group1 pathway1 2 3
group1 pathway4 5 6
group1 pathway2 3 4
group2 pathway2 1 4
group2 pathway3 2 5
答え1
join
これがすることです:
$ join -o 1.1,1.2,1.3,2.2 -12 -21 <(sort -k2 file2) <(sort file1)
group1 pathway1 2 3
group2 pathway2 1 4
group1 pathway2 3 4
group2 pathway3 2 5
group1 pathway4 5 6
または、入力ファイルが実際に提案されているようにコンマで区切られているが質問に表示されない場合:
$ join -t, -o 1.1,1.2,1.3,2.2 -12 -21 <(sort -t, -k2 file2) <(sort file1)
group1,pathway1,2,3
group2,pathway2,1,4
group1,pathway2,3,4
group2,pathway3,2,5
group1,pathway4,5,6
join
両方のファイルの行は共通フィールドにリンクされます。-o
出力形式を設定します。ここでは、最初のファイル(1.1,1.2,1.3
)のフィールド1、2、3を印刷してから、2番目のファイル()の2番目のフィールドを印刷するように指示します2.2
。そして、各ファイルに接続フィールドを設定します-1
。-2
つまり、-12 -21
「file1の2番目のフィールドとfile2の最初のフィールドを結合する」という意味です。最後に、join
入力をソートする必要があるため、両方のファイルをjoin
。
答え2
awkではこれで十分です:
awk 'NR==FNR{a[$1]=$2;next}{print $0,a[$2]}' file1 file2
サンプルファイルはスペースで区切られた形式であり、上記のコードはスペースで区切られたファイルで機能します。
file1 file2 がコンマで区切られている場合は、次のことができます。
awk 'BEGIN{FS=OFS=","}NR==FNR{a[$1]=$2;next}{print $0,a[$2]}' file1 file2
PS:awkでは、FSは入力フィールド区切りに対応し、OFSは出力フィールド区切りに対応します。デフォルトのFSとOFSは「空白」であり、あなたの場合は空白の場合は省略できます(つまり、最初のコードでは省略)。
さまざまな入力フィールド区切り記号とさまざまな出力フィールド区切り文字を組み合わせるには、次のようにします。
awk 'BEGIN{FS=" ";OFS=","}NR==FNR{a[$1]=$2;next};$1=$1{print $0,a[$2]}' file1 file2
#The $1=$1 part is required to redisign the record according to the different Output Field Separator OFS
質問に示すように、スペースで区切られた入力ファイルとカンマで区切られた出力を持つ最後のコードは次のとおりです。
group1,pathway1,2,3
group1,pathway4,5,6
group1,pathway2,3,4
group2,pathway2,1,4
group2,pathway3,2,5
OFS="\t"
PS:スペースで区切られたファイルの場合は、より美しい出力のために(タブ)を指定できます。
答え3
perl -lane '
if ( @ARGV == 1 ) {
$h{ $F[0] } = $F[1];
} else {
print "$_ $h{ $F[1] }";
}
' file1 file2