【问题标题】:Grep for specific numbers within a text file and output per number text fileGrep 获取文本文件中的特定数字并输出每个数字文本文件
【发布时间】:2019-11-14 09:37:43
【问题描述】:

我有一个文本文件 chunk_names.txt,如下所示:

chr1_12334_64321
chr1_134435_77474   
chr10_463252_74754
chr10_54265_423435 
chr13_5464565_547644567

这是一个示例,但表示所有染色体(1...22、X 和 Y)。所有条目都遵循相同的格式chr{1..22, X or Y}_*string of numbers*__*string of numbers*

我想将这些分成每个染色体文件,例如所有从 chr10 开始的块都被放入一个名为 chr10.txt 的文件中:

在 Linux 中我尝试过:

for i in {1..22}
do 
    grep chr$i chunk_names.txt > chr$i.txt 
done 

但是,chr1.txt 输出文件现在包含所有染色体块,其中包含 1(1、10、11、12 等)。

我将如何修改此脚本以分离出染色体?

我还没有解决如何在同一个脚本中包含染色体 X 或 Y,目前正在单独运行它

我尝试过的事情:

grep -o gives me just "chr$i" as an output 
grep 'chr$i' gives me blank files
grep "chr$i" has the initial problem 

非常感谢您的宝贵时间。

【问题讨论】:

    标签: linux grep bioinformatics


    【解决方案1】:

    您的“for”循环意味着解析您的文件 N 次(其中 N 是列表中的染色体/重叠群的数量)。这是一个使用 的不可知方法,它只会解析一次文件:

    awk -F '_' '{ print > $1 ".txt" }' chunk_names.txt
    

    【讨论】:

    • 谢谢史蒂夫!了解这意味着什么:-F 是分隔符,所以 '_' 表示空格吗?打印 $1 是打印列 1 并以 .txt 结尾?
    • -F '_' 指定输入字段分隔符,因此输入行将在_ 处拆分为字段。然后$1 将是第一个字段,即第一个“_”之前的所有内容。 (如果不包含_,则为整行。)不带参数的print 打印整行,> $1 ".txt" 将输出重定向到名为第一个字段($1)的文件,并带有@ 987654330@ 附加,即chr1.txt 等。
    【解决方案2】:

    如果您在数字后面包含_,您可以区分chr1_ 和例如chr10_。要包含 XY,只需将它们包含在循环中

    for i in {1..22} X Y
    do 
        grep "chr${i}_" chunk_names.txt > chr$i.txt 
    done 
    

    要仅在行首搜索,您可以在模式中添加前导 ^

        grep "^chr${i}_" chunk_names.txt > chr$i.txt 
    

    关于您的尝试的说明:

    grep chr$i 在行中的任意位置搜索模式。 shell 将$i 替换为变量i 的值,因此得到chr1chr2 等。

    如果您将模式用双引号括起来为grep "chr$i",shell 将不会执行任何文件名通配符或字符串拆分,但仍会扩展变量。在您的情况下,它与不带引号相同。

    如果您使用单引号,shell 会按原样获取文字字符串,因此您始终会搜索包含 chr$i(而不是 chr1 等)的行,而这不会出现在您的文件中。

    关于引号的解释:

    在您的情况下,我提出的解决方案中的引号不是必需的,但引用所有内容是一个好习惯。如果您的模式包含对 shell 来说特殊的空格或字符,那么引用会有所不同。

    例子:

    如果您的文件包含chr1* 而不是chr1_,则模式chr${i}* 将被匹配文件列表替换。

    当您已经创建了输出文件 chr1.txt 等时,请尝试这些命令

    $ i=1; echo chr$i*
    chr10.txt chr11.txt chr12.txt chr13.txt chr14.txt chr15.txt chr16.txt chr17.txt chr18.txt chr19.txt chr1.txt
    $ i=1; echo "chr$i*"
    chr1*
    

    在第一种情况下,grepcommand

        grep chr${i}* chunk_names.txt
    

    将扩展为

        grep chr10.txt chr11.txt chr12.txt chr13.txt chr14.txt chr15.txt chr16.txt chr17.txt chr18.txt chr19.txt chr1.txt chunk_names.txt
    

    它将在文件chr11.txt ... chr1.txtchunk_names.txt 中搜索模式chr10.txt

    【讨论】:

    • 非常感谢博多!出于兴趣,当我尝试 grep chr${i}_ chunk_names.txt > chr$i.txt 我得到相同的结果(正确的结果)引号的用途是什么?
    • 我将在答案中添加解释。
    • 干杯,感谢您花时间解释这一点,来自非计算背景,让某人逐步解释事情非常有帮助。
    猜你喜欢
    • 2019-07-31
    • 1970-01-01
    • 1970-01-01
    • 2021-05-25
    • 1970-01-01
    • 2013-10-14
    • 2019-04-09
    • 2014-12-19
    • 1970-01-01
    相关资源
    最近更新 更多