15

我有一个日志文件,其中包含许多错误行,例如:

Failed to add email@test.com to database

我可以用一个 grep 调用过滤这些行:

grep -E 'Failed to add (.*) to database'

这很好用,但我真正想做的是让 grep (或我将输出传递到的另一个 Unix 命令)只输出匹配行的电子邮件地址部分。

这可能吗?

4

9 回答 9

14

sed没有 grep 很好:

sed -n 's/Failed to add \(.*\) to database/\1/p' filename
于 2009-06-10T10:33:48.043 回答
8

你也可以只管 grep 到自己:)

grep -E 'Failed to add (.*) to database' | grep -Eo "[^ ]+@[^ ]+"

或者,如果“感兴趣的行”是唯一带有电子邮件的行,则只需使用最后一个 grep 命令而不使用第一个命令。

于 2012-09-04T14:30:34.170 回答
5

您可以使用 sed:

grep -E 'Failed to add (.*) to database'| sed 's/'Failed to add \(.*\) to database'/\1'
于 2009-06-10T10:24:49.887 回答
5

最新版本的 GNU grep 有一个-o选项可以完全满足您的需求。(-o用于--only-matching)。

于 2009-07-16T21:27:10.127 回答
2

这应该做的工作:

grep -x -e '(?<=Failed to add ).+?(?= to database)'

它使用肯定的前瞻断言,然后是电子邮件地址的匹配,然后是 postivie 后瞻断言。这确保它匹配整行,但实际上只使用(并因此返回)电子邮件地址部分。

-x选项指定 grep 应该匹配行而不是整个文本。

于 2009-06-10T10:34:46.513 回答
1

或蟒蛇:

cat file | python -c "import re, sys; print '\r\n'.join(re.findall('add (.*?) to', sys.stdin.read()))"
于 2009-06-10T10:29:13.140 回答
1

-rsed允许不带反斜杠的正则表达式的选项

sed -n -r 's/Failed to add (.*) to database/\1/p' filename
于 2015-04-27T21:46:06.677 回答
0

如果您只想使用 grep 并仅输出匹配的部分行

grep -E -o 'Failed to add (.*) to database'

然后也许如果你想把它写到一个文件中

cat yourlogfile | grep -E -o 'Failed to add (.*) to database' >> outputfile

因此,从 grep 实用程序-o开始 -o, --only-matching show only nonempty parts of lines that match'

于 2022-03-02T07:03:45.980 回答
-2

如果你想使用grep,使用egrep会更合适;

About egrep

Search a file for a pattern using full regular expressions.

grep 并不总是具有完整的正则表达式功能。

于 2009-07-14T17:51:25.597 回答