
私のソースファイル:Test.txt
注:ファイルはタブで区切られており、一部の列には列名がありません。
Chr Start End Alt Value
Exo 0 10 . 1.50 . 20:-2 30:0.9 50:50 50
Exo 1 20 . 1.50 . 20:-1 30:-1 50:50 50
Exo 2 30 . 1.50 . 20:0.02 30:0.9 50:50 50
Exo 3 40 . 1.50 . 20:-1 30:-2 50:50 50
Nem 3 40 . 1.50 . 20:-1 30:-2 50:50 50
上記のファイルに対して次のファイル操作を実装してみてください。たとえば、次のようになります。
1)7列と8列を分割する必要があります。':'変更後は、「mod1」、「mod2」、「mod3」、「mod4」などの列名を指定する必要があります。
2)次に、分割列を「値」列の横に移動し、「mod4」の横に「説明」列をもう1つ配置します(この説明列には空のデータが必要です)。
3) フィルタ列「Mod2」の0.01より大きい値はすべて削除されます。
最終結果は出力フォルダに保存する必要があります。:
Chr Start End Alt Value mod1 mod2 mod3 mod4 comment
Exo 0 10 -1 1.50 20 -2 30 0.9 -1 50:50 50
Exo 1 20 -1 1.50 20 -1 30 -1 -1 50:50 50
Exo 3 40 -1 1.50 20 -1 30 -2 -1 50:50 50
以下を試していくつかのタスクを実装しましたが、そのうちのいくつかは残ります。
#!bin/bash
cd /home/uxm/Desktop/Shell/
# Replace the only dots (.) by -1
awk -F'\t' '{for(i=1;i<=NF;i++){sub(/^\.$/,"-1",$i)}} 1' OFS="\t" Test.txt | tail >> Test1.txt
# splitted 7th no column by delimitted ":"
awk '{ split($7, a, ":"); print $1"\t"$2"\t"$3"\t"$4"\t"$5"\t"$6"\t"a[1]"\t"a[2]"\t"$8"\t"$9"\t"$10"\t"$11 >> "testfile1.tmp"; }' Test1.txt;
mv testfile1.tmp Test2.txt;
# splitted 8th no column by delimitted ":"
awk '{ split($9, a, ":"); print $1"\t"$2"\t"$3"\t"$4"\t"$5"\t"$6"\t"$7"\t"$8"\t"a[1]"\t"a[2]"\t"$10"\t"$11 >> "testfile2.tmp"; }' Test2.txt;
mv testfile2.tmp Test3.txt;
# Give name to splitted columns
awk -F'\t' -v OFS="\t" 'NR==1{$11="nCol\tMod1\tMod2\tMod3\tMod4"}1' Test3.txt >> Test4.txt
# Filter data by "Exo" word
awk -F'\t' 'NR==1;{ if($1 == "Exo") { print }}' Test4.txt | tail >> Test5.txt
答え1
awk
以下は、リストされた手順を実行するスクリプトです。 1つのスクリプトですべての操作を実行するawk
と、複数回実行して中間結果をファイルや変数に保存する必要がないという利点があります。
BEGIN { OFS = FS = "\t" }
NR == 1 {
# Add new column headers
# First four "mod" headers
for (i = 1; i <= 4; ++i)
$(NF + 1) = "mod" i
# Then a "comment" header
$(NF + 1) = "comment"
# Output and continue with next input line
print
next
}
# Ignore lines that don't have "Exo" in the first column
$1 != "Exo" { next }
{
# Working our way "backwards" from column 13 down to 1
# Shift the last two columns right by three steps
$13 = $10
$12 = $9
# Set column 11 to column 6, or to -1 if it's a dot
if ($6 == ".")
$11 = -1
else
$11 = $6
# Empty the comment column
$10 = ""
# Move column 8 into column 9
$9 = $8
# Split column 9 into columns 8 and 9
split($9, a, ":")
$9 = a[2]
$8 = a[1]
# Split column 7 into columns 6 and 7
split($7, a, ":")
$7 = a[2]
$6 = a[1]
# Column 5 remains unmodified
# Put -1 in column 4 if it's a dot
if ($4 == ".") $4 = -1
# Columns 1, 2, 3 remains unmodified
}
# Output if we want this line
$7 <= 0.01 { print }
実行してください:
$ awk -f script.awk Test.txt
Chr Start End Alt Value mod1 mod2 mod3 mod4 comment
Exo 0 10 -1 1.50 20 -2 30 0.9 -1 50:50 50
Exo 1 20 -1 1.50 20 -1 30 -1 -1 50:50 50
Exo 3 40 -1 1.50 20 -1 30 -2 -1 50:50 50
私はあなたのコードであなたがExo
この行だけに興味があると仮定しているので、スクリプトでその行だけを見てみました。Alt
tha列(および最初に名前が付けられていない最初の列)のすべての点をに変更する必要があり、コードを表示して変更することもできる-1
と仮定します。