输入文件看起来像这样:
chr1 1 G 300
chr1 2 A 500
chr1 3 C 200
chr4 1 T 35
chr4 2 G 400
chr4 3 C 435
chr4 4 A 223
chr4 5 T 400
chr4 6 G 300
chr4 7 G 340
chr4 8 C 400
实际文件太大而无法处理,因此我想输出一个较小的文件,按特定范围内的染色体(第1列)和位置(第2列)过滤。
例如,我正在寻找一个 Linux 命令(sed、awk、grep 等),该命令将从chr4
位置 3 到 7 进行过滤。所需的最终输出是:
chr4 3 C 435
chr4 4 A 223
chr4 5 T 400
chr4 6 G 300
chr4 7 G 340
我不想修改原始文件。
答案1
潜在未排序输入文件的解决方案:
sort -k1,1 -k2,2n file | awk '$1=="chr4" && $2>2 && $2<8'
输出:
chr4 3 C 435
chr4 4 A 223
chr4 5 T 400
chr4 6 G 300
chr4 7 G 340
如果输入文件已排序,则足以使用:
awk '$1=="chr4" && $2>2 && $2<8' file
答案2
awk
可能是完成这项工作的最佳工具。一种简单的解决方案与已经给出的解决方案类似,但实际上使用您指定的参数:
awk '$1=="chr4" && $2>=3 && $2<=7'
您可能更喜欢更通用的解决方案,其中涉及将awk
命令放入 shell 脚本中,如下:
#!/bin/sh
if [ "$#" -lt 3 ]
then
echo "Usage: $0 chromosome low_position high_position"
exit 1
fi
chr="$1"
lo="$2"
hi="$3"
shift 3
awk -vchromo="$chr" -vpos1="$lo" -v pos2="$hi" '$1==chromo && $2>=pos1 && $2<=pos2' "$@"
如果运行的参数少于三个,它会提醒您参数应该是什么,然后退出。否则,它将前三个参数保存到 shell 变量中,然后将它们移出参数列表。然后它调用awk
,将 shell 变量值作为awk
变量传递。
您可以通过以下任一方式调用它:
./myscript chr4 3 7 data
或者
./myscript chr4 3 7 < data
或者
(一些其他进程)| ./myscript chr4 3 7并且,无论如何,将输出重定向到带有
>
.
答案3
您可以使用 grep 完成此操作:
grep -e '^chr4\s\+[3-7]' input
其中表达式为:以 chr4(一个或多个空格字符)^chr4
开头的行,匹配 3 到 7 范围内的一位数字。\s\+
[3-7]
也许更有用的是使用head
或tail
给你尽可能多的行,而不是匹配它们grep
(仅使用 grep 来匹配第一列)。
grep -e '^chr4\s\+' input| tail -n +3| head -n 5
grep
匹配以 开头的行chr4
,tail
给出从第 3 行开始的行,并使用head
限制输出到前 5 行(第 3 行到第 7 行)。
答案4
您可以使用该split
实用程序。
split -p 'chr4 (3|8)' -a 1 my_file output
split
将一个文件分成多个部分(基本上是 的逆cat
)p
根据扩展正则表达式 'chr4 (3|8)' 进行拆分-a 1
使用单个字符为创建的文件添加后缀output
是每个创建的文件的前缀名称
现在该文件outputb
将包含您所需的输出。您还可以修改它以将每个色酮放入其自己的文件中。