Powershell: '$' character matches every character and string

Created on 12 Dec 2018  路  3Comments  路  Source: PowerShell/PowerShell

I discovered this while writing a script that would test a given string against a set of password policies. I noticed "Contains a special character" was always returning True and this is why.

Steps to reproduce

"any character or string" -match "$"

Expected behavior

False

Actual behavior

True

Environment data

Name                           Value
----                           -----
PSVersion                      6.0.2
PSEdition                      Core
GitCommitId                    v6.0.2
OS                             Darwin 16.7.0 Darwin Kernel Version 16.7.0: Thu Jun 21 20:07:39 PDT 2018; root:xnu-3789.73.14~1/RELEASE_X86_64
Platform                       Unix
PSCompatibleVersions           {1.0, 2.0, 3.0, 4.0...}
PSRemotingProtocolVersion      2.3
SerializationVersion           1.1.0.1
WSManStackVersion              3.0

I also tested this in Powershell 5.1. Perhaps I'm misunderstanding the purpose of -match ?

Issue-Question Resolution-Answered

Most helpful comment

-match uses regex matching.

$ in regex is a special character that matches "the end of a string" and is usually used to, for example, check if a string ends with a certain sequence (e.g., -match '\d{4}$' can be used to check if a string _ends_ in 4 digits; without that $ anchor, it would match anywhere in the string.)

If you need literal characters with -match you can escape special characters with a backslash \ if you know which ones need the escaping, or you can generate an escaped string with [Regex]::Escape($string) which will give you a valid regex literal string to match against.

Alternately, you can use -like with appropriate wildcards instead, or even the $String.Contains() method:

$string -like '*$*'
$string.Contains('$')

See Get-Help about_Operators and its related topics specific to -match and its kindred regex operators -replace and -split 馃槃

All 3 comments

-match uses regex matching.

$ in regex is a special character that matches "the end of a string" and is usually used to, for example, check if a string ends with a certain sequence (e.g., -match '\d{4}$' can be used to check if a string _ends_ in 4 digits; without that $ anchor, it would match anywhere in the string.)

If you need literal characters with -match you can escape special characters with a backslash \ if you know which ones need the escaping, or you can generate an escaped string with [Regex]::Escape($string) which will give you a valid regex literal string to match against.

Alternately, you can use -like with appropriate wildcards instead, or even the $String.Contains() method:

$string -like '*$*'
$string.Contains('$')

See Get-Help about_Operators and its related topics specific to -match and its kindred regex operators -replace and -split 馃槃

Thanks so much for the explanation @vexx32, I've been using match differently than its intended for so long that I didn't bother checking the help. Sorry!

No worries @cbrit!

If you ever need someplace to experiment with regex with decent explanations, I've used https://regex101.com and https://regexstorm.net with pretty good success! 馃槃

Was this page helpful?
0 / 5 - 0 ratings