我有以下格式的文件。
I PRP B-PRP
am VBP B-VBP
a DT B-DT
happy JJ B-JJ
soul NN B-NN
I PRP B-PRP
am VBP B-VBP
a DT B-DT
sad JJ B-JJ
soul NN B-NN每条记录都用空行分隔。每一行有3个字段。
如果有一个输入,我是一个快乐的灵魂,我想搜索在这个文件和删除记录,如果它是存在的。在本例中,记录1将从文件中删除。因为句子是多行的,所以我想不出怎么做。我试过sed,awk,grep。似乎什么都起不到作用。基本上,我不知道如何给出这些命令的模式。
sed -e '/I/,/soul/!d' filename 大多数注释都类似于上述类型,begin模式后面跟着end模式。但这在我的案子里行不通。
如何解决这个问题?
发布于 2017-02-09 12:41:49
如果有一个输入,我是一个快乐的灵魂,我想搜索在这个文件和删除记录,如果它是存在的。
您可以使用以下awk命令:
awk -v RS= '!/^I .*\nam .*\nhappy .*\nsoul /' file
I PRP B-PRP
am VBP B-VBP
a DT B-DT
sad JJ B-JJ
soul NN B-NN发布于 2017-02-09 12:34:37
使用AWK可以将RS (记录分隔器)设置为nothing,在空行上拆分记录:
$ awk '/I.*am.*happy.*soul/' RS= input.txt
I PRP B-PRP
am VBP B-VBP
a DT B-DT
happy JJ B-JJ
soul NN B-NN.*是两个正则元字符,.表示任意字符,而*表示零次或多次。
我不确定.与换行符匹配的定义有多好。
发布于 2017-02-09 12:46:10
确切的方法(除了顺序之外,这需要a[$i]=i和... ("am" in a) && a["I"]<a["am"] && ...):
$ awk -v RS= '
{
delete a;
for(i=1;i<=NF;i++) # iterate every word
a[$i] # and store it
}
("I" in a) && ("am" in a) && ("a" in a) && ("happy" in a) && ("soul" in a) {next} 1
' test
I PRP B-PRP
am VBP B-VBP
a DT B-DT
happy JJ B-JJ
soul NN B-NN编辑:测试准确的单词匹配和块中单词的顺序的版本(在本例中为记录),并接受搜索的单词作为参数(参见代码中的s ):
$ awk -v ORS="\n\n" -v RS= -v s="I am a happy soul" '
BEGIN {
n=split(s,a) # split the searched sentance to a hash
}
{
delete b; # delete b or block words
for(i=1;i<=NF;i++) # iterate thru all words
b[$i]=i; # give each word ad order (* see below)
for(i=1;i<=(n-1);i++) # for each word in a see the order of block words
if(b[a[i]]>b[a[i+1]]) # printing at first mismatch
print $0
}' test(*) --我没有测试如果一个想要的词在word块中存在两次会发生什么。最后的位置仍然是那个词所以去想想..。
https://stackoverflow.com/questions/42136789
复制相似问题