Awk 过滤掉文件2中的行,因为对于类似的chr值,文件2的列值在文件1的列2和列3的值范围内
我有两个文件如下所示,其中chr从1到22。我想使用文件1中的chr和pos1 pos 2并过滤掉文件2中的行,因为对于相同的chr,它们的pos1值位于文件1中的pos1和pos2之间,如下所示 文件1Awk 过滤掉文件2中的行,因为对于类似的chr值,文件2的列值在文件1的列2和列3的值范围内,awk,filter,range,Awk,Filter,Range,我有两个文件如下所示,其中chr从1到22。我想使用文件1中的chr和pos1 pos 2并过滤掉文件2中的行,因为对于相同的chr,它们的pos1值位于文件1中的pos1和pos2之间,如下所示 文件1 chr pos1 pos2 1 2389078 2489001 1 2800001 3023010 1 2567898 2708901 3 5647956 6356191 4 5668887 6757869 文件2: chr pos1 1 2460067 1 2
chr pos1 pos2
1 2389078 2489001
1 2800001 3023010
1 2567898 2708901
3 5647956 6356191
4 5668887 6757869
文件2:
chr pos1
1 2460067
1 2389080
3 5508907
输出文件:
chr pos1
1 2460067
1 2389080
我已尝试运行一些类似的解决方案,如以下解决方案:
awk'NR==FNR{start[$1]=$2;end[$1]=$3;next}(FNR==1)| |($1在start中)&&($2>=start[$1])&($2作为文件1
中的chr
重复,数组中的start
和end
脚本被具有相同chr
的值覆盖。请尝试:
awk '
# check if "pos" is between pos1 and pos2 in the passed "ch"
func inrange(ch, pos) {
for (i in chr) {
if (chr[i] == ch && pos >= start[i] && pos <= end[i]) return 1
}
return 0 # no match
}
NR==FNR {
if (NR > 1) { # skip the header line
chr[++n] = $1 # "n" works as an id
start[n] = $2
end[n] = $3
}
next
}
FNR==1 || inrange($1, $2) # print the "filtered" line in file2
' file1 file2
如果输出顺序无关紧要,则对阵列阵列使用GNU awk:
$ cat tst.awk
NR==FNR {
chrpos[$1][$2]
next
}
$1 in chrpos {
for (pos in chrpos[$1]) {
if ( ($2 <= pos) && (pos <= $3) ) {
print $1, pos
delete chrpos[$1][pos]
}
}
}
请在您的问题中添加您的努力(以代码的形式),这是为了解决您自己的问题,我们非常鼓励您这样做,谢谢。
$ cat tst.awk
NR==FNR {
chrpos[$1][$2]
next
}
$1 in chrpos {
for (pos in chrpos[$1]) {
if ( ($2 <= pos) && (pos <= $3) ) {
print $1, pos
delete chrpos[$1][pos]
}
}
}
$ awk -f tst.awk file2 file1
chr pos1
1 2389080
1 2460067