如何查找/grep string1 和 string2 之间的内容?

如何查找/grep string1 和 string2 之间的内容?

我正在尝试从可能随时间变化的长字符串中提取一个值。例如,字符串可能看起来像这样

....../filename-1.9.0.3.tar.gz"<....

我想要提取的是之间的值文件名-.tar.gz,本质上是文件版本(在本例中为 1.9.0.3)。我需要这样做的原因是因为我稍后可能会运行该命令,并且该值将是 1.9.0.6 或 2.0.0.2 或完全不同的值。

我怎样才能做到这一点?我目前只使用 grep,但我不介意使用其他实用程序,例如 sed 或 awk 或 cut 等。为了完全清楚,我只需要提取字符串的文件版本部分,因为它很长(两侧),其他所有内容都需要以某种方式删除。

答案1

对于grep -P/ pcregrep,使用正向后视和正向前视:

grep -P -o '(?<=STRING1).*?(?=STRING2)' infile

在你的情况下替换STRING1filename-STRING2\.tar\.gz


如果您无权访问pcregrep和/或如果您grep不支持,-P您可以使用您最喜欢的文本处理工具来完成此操作。这是一种可移植的方式,可以为ed您提供相同的输出:

ed -s infile <<\IN
g/STRING1/s//\ 
&/g
v/STRING1.*STRING2/d
,s/STRING1//
,s/STRING2.*//
,p
IN

它是如何工作的:在每个出现的地方添加一个换行符STRING1(所以现在每行最多出现一次),然后STRING1.*STRING2删除所有不匹配的行;对于其余的,我们只保留 和 之间的内容STRING1STRING2打印结果。

答案2

为了那些没有 POSIX 系统的人的利益grep -P,您可以使用任何 POSIX 系统sedawk在任何 POSIX 系统上执行此操作。

sed -n -e 's/^.*\/filename-\([^\/]*\)\.tar\.gz.*$/\1/p' -e T -e q

说明:关闭默认打印,找到包含所需模式的行,并替换除要保留的部分之外的所有内容,打印替换结果,如果匹配则退出。请注意,如果第一个匹配行上有多个匹配项,则会选取最后一个匹配项。

使用 awk(选择该行的第一个匹配项):

awk 'match($0, /filename-[^/]*\.tar\.gz/) {
    print substr(RSTART + 9, RSTART + RLENGTH - 9 - 6, $0);
    exit;
}'

相关内容