我有一个带有许多功能的制表符分隔文件。我想删除信息量最少的行。具体来说,我想删除所有列中除了可以有yes或no之外的所有列都有问号(?)的行。我的文件看起来像
a b c frequent
? ? ? No
? ? 1 Yes
1 ? 1 No
? 1 1 Yes
? ? ? No
? ? ? Yes
我想删除包含
的列? ? ? No
或
? ? ? Yes
我可以用
sed '/pattern/d' ./ file
我但是如何将它用于多个副本?可以有数百个列的解决方案,例如
sed '/? ? ? No/d' ./ file
和
sed '/? ? ? Yes/d' ./ file
不起作用。我希望我的输出看起来像
a b c frequent
? ? 1 Yes
1 ? 1 No
? 1 1 Yes
编辑1:对于制表符分隔文件中的列,第一列为序列号,最后一列为空格分隔的类标签。我想考虑倒数第二行的第二行,并删除包含所有问号的列。
No a b c itemname
1 ? ? ? frying pan
2 ? ? 1 t-shirt
3 1 ? 1 microwave oven
10 ? 1 1 forks and knives
11 ? ? ? gold
12 ? ? ? chain
想要的输出是
No a b c itemname
2 ? ? 1 t-shirt
3 1 ? 1 microwave oven
10 ? 1 1 forks and knives
答案 0 :(得分:3)
逃离?
sed '/\? +\? +\? +Yes/d' file
由于您的文件似乎是以多个空格分隔的空间,因此您需要+
或者如果你有tab
sed '/\?\t\?\t\?\tNo/d' file
awk
解决方案,用于删除仅包含?
awk '{for (i=1;i<NF;i++) if ($i!~"?") f=1} f {print;f=x}' file
或者使用aragaers方法,仅打印至少有一个1
awk '/1/ || NR==1' file
a b c frequent
? ? 1 Yes
? ? 1 Yes
答案 1 :(得分:3)
您可以尝试一步处理这两种情况
sed -r '/(\?\s+){3}(Yes|No)/d' ./file
修改强>
关于每行?
的数量,如果您想要“一个或多个”或使用{{1},则可以将{3}
替换为+
如果您想要“ 3或更多”之类的内容,或者您可以使用{3,}
例如,如果您想说“介于3和5之间”< / p>
<强> EDIT2:强>
这是一个grep替代
{3,5}
注意强>:
egrep -v '(\?\s+){3}(Yes|No)' ./fileToTest > outputFile
无效的原因是因为我们在检查了sed的帮助后需要sed
我发现它是标志extended regex
答案 2 :(得分:2)
是否保证该列包含?
或1
?如果是,只需删除所有内容,除非它至少包含一个1
(并且不是第一行):
sed -n '1p; /1/p;' file
答案 3 :(得分:0)
使用awk
:
[ ~]$ cat test.txt
a b c frequent
? ? ? No
? ? 1 Yes
1 ? 1 No
? 1 1 Yes
? ? ? No
? ? ? Yes
[ ~]$ awk '!($0 ~ "?\\ *?\\ *?\\ *(Yes|No)"){print}' test.txt
a b c frequent
? ? 1 Yes
1 ? 1 No
? 1 1 Yes
[ ~]$
你也可以像这样使用egrep
:
[ ~]$ egrep -v "\?\ *\?\ *\?\ *(Yes|No)" test.txt
a b c frequent
? ? 1 Yes
1 ? 1 No
? 1 1 Yes
答案 4 :(得分:0)
关于您的上次更新,您可以按如下方式修改@Jotne的解决方案:
NR==1 {
p=NF-2
next
}
{
for (i=1;i<=p;i++) {
if (!( $(i+1)=="?")) f=1
}
}
f {
print
f=x
}