亲爱的,我需要一些帮助。
我有这个输入文件:
chr1
chr1
chr2
chr2
chr3
chr3
我想将它分成以下输出文件:
"第一个文件"
chr1
chr1
chr1
"第二个文件"
chr2
chr2
"第三个文件"
chr3
chr3
我正在使用此代码,但它无效
for i in {1..3}
do
awk '{if ($1 == "chr"$i) {print $0}}' 17_n.tsv > $i
done
答案 0 :(得分:1)
也许你可以使用这样的东西:
$ cat file
chr1
chr1
chr2
chr2
chr3
chr3
$ awk '{suffix = substr($1, length($1)); print > "file" suffix}' file
$ cat file1
chr1
chr1
$ cat file2
chr2
chr2
$ cat file3
chr3
chr3
基本上,取第一个字段的最后一个字符并用它来确定文件名。
如果最后可以有多个数字,您可以改用:
awk 'match($1, /[0-9]+$/) { print > ("file" substr($1, RSTART)) }' file
match
将RSTART
设置为匹配开头的位置,因此可以与substr
一起使用以提取输入的数字部分。
答案 1 :(得分:1)
如果您的行格式为N non-number chars + N numbers
,则可以尝试:
awk '{f=$0;sub(/^[^0-9]*/,"",f);print >("output"f)}' input
这对ch0r1
无效。
如果您希望它也适用于ch0r1
,请使用 gawk :
awk '{f=gensub(/^.*[^0-9]([0-9]*)$/,"\\1","g");print >("output"f)}' file
答案 2 :(得分:1)
由于awk
是一种与其自己的解释器不同的语言,bash
变量无法在awk
中正确使用而不首先使用-v
选项传递它们。另外,awk
中的默认操作是打印,因此您不需要{print $0}
。
所以这会奏效:
for i in {1..3}
do
awk -v i=$i '$1 == "chr"i' 17_n.tsv > $i
done
也就是说,你也可以在read
循环中完成你想要的东西:
while read -r line
do
[[ $line == chr+([0-9]) ]] && echo $line >> ${line#chr}
done < 17_n.tsv