我的文件包含
等行GRANT SELECT ON USER.TABLE1 TO USER1
/
GRANT INSERT ON USER.TABLE1 TO USER1
/
GRANT UPDATE ON USER.TABLE1 TO USER1
/
GRANT DELETE ON USER.TABLE1 TO USER1
/
GRANT SELECT ON USER.TABLE1 TO USER2
/
GRANT INSERT ON USER.TABLE1 TO USER2
/
GRANT UPDATE ON USER.TABLE1 TO USER2
......等等......
sed命令我正在寻找或者更好地寻找穿过两条线的模式, 应该删除" GRANT .."行加上后来的行以" /"。
开头你们的任何解决方案都是大师吗?
答案 0 :(得分:2)
sed '/^GRANT/ { N; d }' filename
当遇到以GRANT
开头的行时,会获取下一行并弃掉它们。
仅在下一行以GRANT
开头时删除/
行,
sed ':a /^GRANT/ { N; /\n\//! { P; s/.*\n//; ba }; d }' filename
的工作原理。这很复杂,主要是因为两条GRANT
行可能会一个接一个地直接出现,如
GRANT foo
GRANT bar
/
必须删除GRANT bar
和/
并且GRANT foo
保持不变:
:a # jump label for looping
/^GRANT/ { # if a line begins with GRANT
N # fetch the next line
/\n\//! { # if the next line does not begin with /
P # print the first
s/.*\n// # remove it
ba # go back to :a
}
d # otherwise discard both
}
或者,在将文件完全读入内存后使用多行正则表达式(假设它适合那里):
sed ':a $!{N; ba}; s/\(^\|\n\)GRANT[^\n]*\n\/[^\n]*//g' filename
,其中
:a $!{N; ba} # read whole file into the pattern space
s/\(^\|\n\)GRANT[^\n]*\n\/[^\n]*//g # match offending lines by regex and
# remove them
但是,在这一点上,我认为最常见的选择是在多线模式下使用pcregrep
:
pcregrep -vM '^GRANT[^\n]*\n/' filename
答案 1 :(得分:0)
此awk
应该有效:
awk '/^GRANT/ {f=1;next} f && /^\// {f=0;next} 1' file
如果以^GRANT
开头的行,请跳过它并将标记f
设置为true
如果行以/
开头且标记f
为真,则跳过它并重置标记f
1
打印所有其他行。
因此,这只会删除以GRANT
开头的行以及以/
开头的下一行
示例:
cat file
GRANT SELECT ON USER.TABLE1 TO USER1
/
GRANT INSERT ON USER.TABLE1 TO USER1
test
/ should be removed
some other data
/ should not be removed
GRANT UPDATE ON USER.TABLE1 TO USER1
/
GRANT DELETE ON USER.TABLE1 TO USER1
/
GRANT SELECT ON USER.TABLE1 TO USER2
/
GRANT INSERT ON USER.TABLE1 TO USER2
/
GRANT UPDATE ON USER.TABLE1 TO USER2
awk '/GRANT/ {f=1;next} f && /^\// {f=0;next} 1' file
test
some other data
/ should not be removed
答案 2 :(得分:0)
sed用于单行操作。对于跨越线条的任何东西,你应该使用awk。例如使用GNU awk进行多字符RS:
awk -v RS='^$' -v ORS= '{gsub(/GRANT[^\n]+\n[/]\n/,"")}1' file
e.g:
$ cat file
foo
GRANT INSERT ON USER.TABLE1 TO USER1
/
GRANT UPDATE ON USER.TABLE1 TO USER1
intermediate line so leave
/
GRANT DELETE ON USER.TABLE1 TO USER1
/
bar
$ awk -v RS='^$' -v ORS= '{gsub(/GRANT[^\n]+\n[/]\n/,"")}1' file
foo
GRANT UPDATE ON USER.TABLE1 TO USER1
intermediate line so leave
/
bar