PowerShell DISCUSSION

Why do PowerShell comparisons on arrays and on numbers typed by the user give unexpected results?

Started by payam PowerShell comparison operatorsnull comparisontype conversion-eq with arrayscase sensitivity
4 replies 248 views 5 participants
Latest activity · 30 Sep 2026

Why do PowerShell comparisons on arrays and on numbers typed by the user give unexpected results?

payam PowerShell Forum
#1

Three comparisons in my script misbehave. With $levels = 3, 0, 7, the test if ($levels -eq 0) is never true although the array contains a zero, and at the prompt $levels -eq 7 prints 7 rather than True. After $n = Read-Host "Threshold", entering 10 makes if ($n -gt 5) false. And when I wrote if ($count > 10) out of habit, a file named 10 appeared.

How do PowerShell's comparison operators decide what to compare, and what is the safe way to write these checks?

Community replies 4

Re: Why do PowerShell comparisons on arrays and on numbers typed by the user give unexpected results?

#2

When the left operand is an array, a comparison operator acts as a filter: it returns the elements that satisfy the comparison instead of True or False. $levels -eq 7 returns 7, and $levels -eq 0 returns a one-element array containing 0. In an if, a one-element array is converted using that element, and 0 is false, so the branch never runs. For a membership test use $levels -contains 0 or 0 -in $levels, which always return a Boolean.

This is also why null checks are written with the constant on the left: $null -eq $value is always a scalar comparison, whereas $value -eq $null filters when $value happens to be an array.

Re: Why do PowerShell comparisons on arrays and on numbers typed by the user give unexpected results?

#3

For two scalars of different types, the right operand is converted to the type of the left one. Read-Host always returns a string, so $n -gt 5 with $n equal to "10" converts the 5 to "5" and compares text, and "10" sorts before "5". Swap the sides and it becomes numeric: 5 -lt $n converts "10" to a number and is true.

Rather than depend on operand order, convert the input once: [int]$n = Read-Host "Threshold". That also rejects non-numeric input with a clear conversion error at the point where it is entered.

Re: Why do PowerShell comparisons on arrays and on numbers typed by the user give unexpected results?

#4

The operators are words because the symbols were already taken by the shell: > and < are redirection, and = is assignment. So $count > 10 writes the value of $count to a file called 10, and if ($x = 5) assigns 5 and is always true. The set is -eq, -ne, -gt, -ge, -lt, -le, plus -like for wildcard patterns and -match for regular expressions, which fills $Matches with the captured groups.

String comparisons ignore case by default: 'ABC' -eq 'abc' is True. Prefix the operator with c for case-sensitive versions, as in -ceq, -clike and -cmatch.

Re: Why do PowerShell comparisons on arrays and on numbers typed by the user give unexpected results?

#5

Two frequent mix-ups. -contains tests whether a collection has an element; it is not a substring test, so 'firmware.hex' -contains 'hex' is False. For substrings use -like '*hex*', -match 'hex' or the .Contains('hex') string method (the method is case-sensitive).

And truthiness in if ($value) has its own rules: $null, 0, an empty string and an empty array are false, and a single-element array takes the value of its element. To test whether a command returned anything, wrap it and count: $files = @(Get-ChildItem *.log) then if ($files.Count -eq 0).

TEP COMMUNITY