about_Regular_Expressions
简短说明
介绍 PowerShell 中的正则表达式。
长说明
注意
本文将介绍在 PowerShell 中使用正则表达式的语法和方法,但并未讨论所有语法。 有关更完整的参考,请参阅 正则表达式语言 - 快速参考。
正则表达式是用于匹配文本的模式。 它可以由文本字符、运算符和其他构造组成。
本文演示 PowerShell 中的正则表达式语法。 PowerShell 具有多个使用正则表达式的运算符和 cmdlet。 可以在以下链接中详细了解其语法和用法。
PowerShell 正则表达式默认不区分大小写。 上面所示的每种方法都有不同的方法来强制区分大小写。
- 对于
Select-String
,请使用 CaseSensitive 参数。 - 对于使用正则表达式的运算符,请使用区分大小写的版本:
-cmatch
、-creplace
或-csplit
switch
对于 语句,请使用-casesensitive
选项
字符文本
正则表达式可以是文本字符或字符串。 表达式会导致引擎完全匹配指定的文本。
# This statement returns true because book contains the string "oo"
'book' -match 'oo'
字符类
如果知道确切的模式,字符文本可以正常工作,但字符类允许你不太具体。
字符组
[character group]
允许一次匹配任意数量的字符,而 [^character group]
仅匹配组中的字符。
# This expression returns true if the pattern matches big, bog, or bug.
'big' -match 'b[iou]g'
如果要匹配的字符列表包括) (-
连字符,则它必须位于列表的开头或末尾才能将其与字符范围表达式区分开来。
字符范围
模式也可以是一系列字符。 字符可以是字母、 [A-Z]
数字 [0-9]
,甚至基于 [ -~]
ASCII 的字符 (所有可打印字符) 。
# This expression returns true if the pattern matches any 2 digit number.
42 -match '[0-9][0-9]'
数字
\d
字符类将匹配任何十进制数字。 相反, \D
将匹配任何非十进制数字。
# This expression returns true if it matches a server name.
# (Server-01 - Server-99).
'Server-01' -match 'Server-\d\d'
Word个字符
字符 \w
类将匹配任何单词字符 [a-zA-Z_0-9]
。 若要匹配任何非单词字符,请使用 \W
。
# This expression returns true.
# The pattern matches the first word character 'B'.
'Book' -match '\w'
通配符
句点 (.
) 是正则表达式中的通配符。 它将匹配除换行符 (\n
) 之外的任何字符。
# This expression returns true.
# The pattern matches any 4 characters except the newline.
'a1\ ' -match '....'
空格
可以将任何空格字符与 \s
字符类匹配。 可以将任何非空格字符与 \S
匹配。 可以将文本空格字符与
匹配。
# This expression returns true.
# The pattern uses the whitespace character class to match the leading
# space and a literal space to matching the trailing space.
' - ' -match '\s- '
数量词
限定符控制输入字符串中应存在的每个元素的实例数。
以下是 PowerShell 中提供的一些限定符:
限定符 | 描述 |
---|---|
* |
零次或更多次。 |
+ |
一次或多次。 |
? |
零次或一次。 |
{n,m} |
至少 n 为 ,但不超过 m 次数。 |
星号 (*
) 与上一个元素匹配零次或多次。 结果是,即使没有 元素的输入字符串也是匹配项。
# This returns true for all account name strings even if the name is absent.
'ACCOUNT NAME: Administrator' -match 'ACCOUNT NAME:\s*\w*'
加号 (+
) 与上一个元素匹配一次或多次。
# This returns true if it matches any server name.
'DC-01' -match '[A-Z]+-\d\d'
问号 ?
与上一个元素匹配零或一次。 与星号 *
一样,它甚至会匹配元素不存在的字符串。
# This returns true for any server name, even server names without dashes.
'SERVER01' -match '[A-Z]+-?\d\d'
可以使用 {n, m}
限定符的几种不同方式,以允许对限定符进行精细控制。 第二个元素 m
和逗号 ,
是可选的。
限定符 | 描述 |
---|---|
{n} |
完全 n 匹配的次数。 |
{n,} |
至少 n 匹配次数。 |
{n,m} |
在 和 m 次数之间n 匹配。 |
# This returns true if it matches any phone number.
'111-222-3333' -match '\d{3}-\d{3}-\d{4}'
定位点
通过定位点,可以根据输入字符串中的匹配位置导致匹配成功或失败。
两个常用的定位点是 ^
和 $
。 插入符号 ^
与字符串的开头和 $
匹配字符串的末尾。 通过定位点,可以在特定位置匹配文本,同时放弃不需要的字符。
# The pattern expects the string 'fish' to be the only thing on the line.
# This returns FALSE.
'fishing' -match '^fish$'
注意
定义包含 $
定位点的正则表达式时,请确保使用单引号 ('
) 而不是双引号将正则表达式括起来, () "
或 PowerShell 会将表达式扩展为变量。
在 PowerShell 中使用定位点时,应了解 单行 和 多行 正则表达式选项之间的区别。
- 多行:多行模式强制
^
和$
匹配每个 LINE 的开头结束而不是输入字符串的开头和结尾。 - 单行:单行模式将输入字符串视为 单行。
它强制
.
字符匹配每个字符 (包括换行符) ,而不是匹配除换行符\n
以外的每个字符。
若要详细了解这些选项及其用法,请访问 正则表达式语言 - 快速参考。
转义字符
反斜杠 (\
) 用于转义字符,因此它们不会被正则表达式引擎分析。
保留以下字符: []().\^$|?*+{}
。
你需要在模式中转义这些字符,以匹配输入字符串中的这些字符。
# This returns true and matches numbers with at least 2 digits of precision.
# The decimal point is escaped using the backslash.
'3.141' -match '3\.\d{2,}'
正则表达式类有一个静态方法,可以为你转义文本。
[regex]::escape('3.\d{2,}')
3\.\\d\{2,}
注意
这会转义所有保留的正则表达式字符,包括字符类中使用的现有反斜杠。 请确保仅在需要转义的模式部分使用它。
其他字符转义
还可以使用保留字符转义来匹配特殊字符类型。
下面是一些常用的字符转义:
字符转义 | 说明 |
---|---|
\t |
匹配选项卡 |
\n |
匹配换行符 |
\r |
匹配回车符 |
组、捕获和替换
分组构造将输入字符串分隔为可以捕获或忽略的子字符串。 分组的子字符串称为 subexpressions。 默认情况下,子表达式在编号组中捕获,但也可以为其分配名称。
分组构造是用括号括起来的正则表达式。 捕获由封闭的正则表达式匹配的任何文本。 以下示例将输入文本分为两个捕获组。
'The last logged on user was CONTOSO\jsmith' -match '(.+was )(.+)'
True
使用 $Matches
哈希表 自动变量检索捕获的文本。
表示整个匹配的文本存储在键 0
中。 请务必注意, $Matches
哈希表仅包含任何匹配模式的第一个匹配项。
$Matches.0
The last logged on user was CONTOSO\jsmith
捕获存储在从左到右的 整数 键中。 捕获 1
包含所有文本,直到用户名,捕获 2
仅包含用户名。
$Matches
Name Value
---- -----
2 CONTOSO\jsmith
1 The last logged on user was
0 The last logged on user was CONTOSO\jsmith
重要
键 0
是 整数。 可以使用任何 Hashtable 方法来访问存储的值。
PS> 'Good Dog' -match 'Dog'
True
PS> $Matches[0]
Dog
PS> $Matches.Item(0)
Dog
PS> $Matches.0
Dog
命名捕获
默认情况下,捕获按从左到右的数值升序存储。
还可以将 名称 分配给捕获组。 此名称将成为 Hashtable 自动变量上的$Matches
键。
在捕获组中,使用 ?<keyname>
将捕获的数据存储在命名键下。
PS> $string = 'The last logged on user was CONTOSO\jsmith'
PS> $string -match 'was (?<domain>.+)\\(?<user>.+)'
True
PS> $Matches
Name Value
---- -----
domain CONTOSO
user jsmith
0 was CONTOSO\jsmith
PS> $Matches.domain
CONTOSO
PS> $Matches.user
jsmith
以下示例将最新的日志条目存储在 Windows 安全中心 日志中。 提供的正则表达式从消息中提取用户名和域,并将其存储在 key:N 表示 name,D 表示域。
$log = (Get-WinEvent -LogName Security -MaxEvents 1).message
$r = '(?s).*Account Name:\s*(?<N>.*).*Account Domain:\s*(?<D>[A-Z,0-9]*)'
$log -match $r
True
$Matches
Name Value
---- -----
D CONTOSO
N jsmith
0 A process has exited....
有关详细信息,请参阅 正则表达式中的分组构造。
正则表达式中的替代
将正则表达式 (正则表达式) 与 -replace
运算符配合使用,可以使用捕获的文本动态替换文本。
<input> -replace <original>, <substitute>
<input>
:要搜索的字符串<original>
:用于搜索输入字符串的正则表达式<substitute>
:一个正则表达式替换表达式,用于替换在输入字符串中找到的匹配项。
<original>
和 <substitute>
操作数受正则表达式引擎的规则约束,例如字符转义或替换表达式。 替换模式可以包含一个或多个替换以及本文字符。
可以使用组标识符前的字符在 <substitute>
字符串 $
中引用捕获组。
引用捕获组的两种方法是 按数字 和 按名称。
按数字 - 捕获组从左到右进行编号。
'John D. Smith' -replace '(\w+) (\w+)\. (\w+)', '$1.$2.$3@contoso.com'
John.D.Smith@contoso.com
按名称 - 捕获组也可以按名称引用。
'CONTOSO\Administrator' -replace '\w+\\(?<user>\w+)', 'FABRIKAM\${user}'
FABRIKAM\Administrator
表达式 $&
表示匹配的所有文本。
'Gobble' -replace 'Gobble', '$& $&'
Gobble Gobble
警告
由于字符 $
用于字符串扩展,因此需要使用带替换的文本字符串,或者在使用双引号时转义 $
字符。
'Hello World' -replace '(\w+) \w+', '$1 Universe'
"Hello World" -replace "(\w+) \w+", "`$1 Universe"
Hello Universe
Hello Universe
此外,如果要将 $
用作文本字符,请使用 $$
而不是普通转义字符。 使用双引号时,仍会转义 的所有实例 $
,以避免不正确的替换。
'5.72' -replace '(.+)', '$$$1'
"5.72" -replace "(.+)", "`$`$`$1"
$5.72
$5.72
有关替换表达式的详细信息,请参阅 正则表达式中的替换。