【发布时间】:2015-01-28 19:26:22
【问题描述】:
我正在尝试弄清楚如何制作一个包含 ID 和基因的 .txt 文件 (myGeneFile.txt),如下所示:
Probe Set ID Gene Symbol
1007_s_at DDR1 /// MIR4640
1053_at RFC2
117_at HSPA6
121_at PAX8
1255_g_at GUCA1A
1294_at MIR5193 /// UBA7
进入这个:
DDR1
MIR4640
RFC2
HSPA6
PAX8
GUCA1A
MIR5193
UBA
首先我尝试这样做:
cat myGeneFile.txt | tail -n +2 | awk '{split($2,a,"///"); print a[1] "\t" a[2] "\t" a[3] "\t" a[4] "\t" a[5];}' > test.txt
(即,我删除了文件的顶部(标题)行,我尝试沿分隔符 /// 拆分第二行,然后打印任何可能出现的基因)
然后,我尝试这样做:
cat myGeneFile.txt | tail -n +2 | awk '{print $2}' | grep -o -E '\w+' > test.txt
(字面上列出第二列中的所有单词)
在这两种情况下,我得到了相同的输出 - 每行中只有第一个基因的长列表(例如,MIR4640 和 UBA7 缺失)
有什么想法吗?
编辑:感谢@CodeGnome 的帮助。我最终使用了该代码并对其进行了修改,因为我发现我的文件每行有 1 到 30 个不同的基因名称。所以,我用了:
awk 'NR == 1 {next}
{
sub("///", "")
print $2 }
{ for (i=3; i<=30; i++)
if ($i) {print $i}
}' myGeneFile.txt > test2.txt
@GlenJackson 也有一个非常有效的解决方案:
awk 'NR>1 {for (i=2; i<=NF; i++) if ($i != "///") print $i}' file
【问题讨论】:
-
您假设
awk理解您对“列”的定义。它没有。默认情况下,awk 按空格分割字段,因此1007_s_at DDR1 /// MIR4640行是四个 字段而不是两个。1007_s_at、DDR1、///和MIR4640。如果您的输入是制表符分隔的,那么告诉awk只在制表符上拆分,您的第一次尝试会更好。 -
@EtanReisner 您可以在操作中使用 sub() ,然后 awk 将只看到 2-3 个字段。 OP 的部分问题是他的数据具有可变数量的字段。我在下面的my answer 中解决了这个问题。
-
@CodeGnome 可变数量的字段不是问题,我知道 awk 可以做什么。您的解决方案是特定于字段计数的,不需要如此。
-
太棒了!很高兴您在@GlenJackman 的回答和我的回答中都找到了一些有用的想法。通常有不止一种方法可以解决大多数问题,看到多种方法并从其他方法中综合出您自己的解决方案会非常有帮助。祝你的基因研究好运!