Regex 用grep在一行中捕获正则表达式
在bash中,我的计算机上传感器的输出如下所示:Regex 用grep在一行中捕获正则表达式,regex,bash,grep,Regex,Bash,Grep,在bash中,我的计算机上传感器的输出如下所示: Adapter: ISA adapter Physical id 0: +67.0°C (high = +84.0°C, crit = +100.0°C) Core 0: +65.0°C (high = +84.0°C, crit = +100.0°C) Core 1: +65.0°C (high = +84.0°C, crit = +100.0°C) Core 2: +65.0°C (h
Adapter: ISA adapter
Physical id 0: +67.0°C (high = +84.0°C, crit = +100.0°C)
Core 0: +65.0°C (high = +84.0°C, crit = +100.0°C)
Core 1: +65.0°C (high = +84.0°C, crit = +100.0°C)
Core 2: +65.0°C (high = +84.0°C, crit = +100.0°C)
Core 3: +67.0°C (high = +84.0°C, crit = +100.0°C)
我需要在bash中的一行中捕获物理id 0之后的温度及其单位
所以在这里,我希望命令精确返回67.0°C
我尝试链接grep
命令,下面是我的尝试
sensors | grep -oEi "id[^C]+C" | grep -oEi "[\d.]+°C"
由于grep似乎不可能进行分组,第一组用于捕获ID0:+67.0°C
,第二组67.0°C
但是,没有返回任何内容。不过,第一个grep似乎已经返回了它应该返回的内容
那么如何捕捉这个字符串呢?
如果bash中只有一行,任何其他技术都可以。您可以使用
s='Physical id 0: +67.0°C (high = +84.0°C, crit = +100.0°C)'
echo $s | grep '^Physical id 0:' | awk '{print $4}'
看
在这里,grep'^Physical id 0:'
获取以Physical id 0:
子字符串开头的行(注意,^
是regex中行锚的开头),然后awk
打印第4列(因为awk
使用制表符和空格将行拆分为列)
这种方法利用了以下事实:字符串结构良好,并且在物理id 0:
之后始终存在以摄氏度为单位的温度
如果您需要更好的精度,并且可以访问GNUgrep
,您可以使用PCREgrep
选项p
来使用PCRE模式,如
sensors | grep -oP 'Physical\s+id\s+\d+:\s+\K[0-9+.]+°C'
要获得1+位数,+
或
符号后跟°C
详细信息:
$ sensors | sed -E -n 's/^Physical id 0: \+([^ ]*).*/\1/p'
67.0°
-文字子字符串物理
-1+空格\s+
-id\s+
和1+空格id
-1+位\d+
-冒号:
-1个或多个空格\s+
-匹配重置运算符,该运算符将丢弃迄今为止匹配的所有文本\K
-1个或多个字符,可以是数字、[0-9+.]+
或+
- <代码>°C-文字
text°C
s='Physical id 0: +67.0°C (high = +84.0°C, crit = +100.0°C)'
echo $s | grep '^Physical id 0:' | awk '{print $4}'
看
在这里,grep'^Physical id 0:'
获取以Physical id 0:
子字符串开头的行(注意,^
是regex中行锚的开头),然后awk
打印第4列(因为awk
使用制表符和空格将行拆分为列)
这种方法利用了以下事实:字符串结构良好,并且在物理id 0:
之后始终存在以摄氏度为单位的温度
如果您需要更好的精度,并且可以访问GNUgrep
,您可以使用PCREgrep
选项p
来使用PCRE模式,如
sensors | grep -oP 'Physical\s+id\s+\d+:\s+\K[0-9+.]+°C'
要获得1+位数,+
或
符号后跟°C
详细信息:
$ sensors | sed -E -n 's/^Physical id 0: \+([^ ]*).*/\1/p'
67.0°
-文字子字符串物理
-1+空格\s+
-id\s+
和1+空格id
-1+位\d+
-冒号:
-1个或多个空格\s+
-匹配重置运算符,该运算符将丢弃迄今为止匹配的所有文本\K
-1个或多个字符,可以是数字、[0-9+.]+
或+
-文字°C
文字°C
- 带awk:
sensors | awk '/^Physical id 0:/ {print $4}'
输出:
+67.0°C
+67.0摄氏度
使用awk:
sensors | awk '/^Physical id 0:/ {print $4}'
输出:
+67.0°C
+67.0摄氏度
纯粹的狂欢。首先是“大”的方式来更好地理解它,然后是“一行”风格
如果不设置变量并直接输入值,则只能在一行中完成。这是“一行”风格:
我改进了正则表达式以处理空格或制表符,因为我不确定两者都可以是什么。我做的另一个小改进是加号“+”符号。它也可以是一个负“-”符号。如果温度低于零,你可能需要它:)纯bash。首先是“大”的方式来更好地理解它,然后是“一行”风格
如果不设置变量并直接输入值,则只能在一行中完成。这是“一行”风格:
我改进了正则表达式以处理空格或制表符,因为我不确定两者都可以是什么。我做的另一个小改进是加号“+”符号。它也可以是一个负“-”符号。如果温度低于零,您可能需要它:)APOSIX兼容的
sed
解决方案,使用BRE(基本正则表达式):
将现代ERE(扩展正则表达式)语法与非标准的-E
选项一起使用-可用于GNUsed
和BSD/macOSsed
:
$ sensors | sed -E -n 's/^Physical id 0: \+([^ ]*).*/\1/p'
67.0°
注意(
和)
如何需要\
-在BREs中转义才能具有语法功能,就像+
那样,因此仅使用+
就意味着文字使用
相反,在ERE中,(
和)
是元字符,就像+
一样,这就是为什么它需要\
-转义才能用于文字
至于你所尝试的:
$ sensors | sed -E -n 's/^Physical id 0: \+([^ ]*).*/\1/p'
67.0°
唯一的问题(不考虑效率)是您试图使用\d
:
$ sensors | sed -E -n 's/^Physical id 0: \+([^ ]*).*/\1/p'
67.0°
- GNU
根本不支持grep
表示数字\d
- BSD/macOS
在字符集(括号表达式)内不支持它(grep
)[…]
0-9
代替\d
可以:
$ sensor | grep -oEi "id[^C]+C" | grep -oEi '[0-9.]+°C'
67.0°C
如果使用-p
不是一个选项(仅GNUgrep
,它启用单通解决方案-请参阅),更简单的双通解决方案是:
$ sensor | grep -oEi "id[^C]+C" | cut -d'+' -f2
67.0°C
符合POSIX标准的sed解决方案,使用BRE(基本正则表达式): 使用非标准的现代ERE(扩展正则表达式)语法