应该使用什么运算符来检测空的psobject?

时间:2018-11-06 23:11:38

标签: powershell

使用以下示例:

$test = '{ }' | ConvertFrom-Json

如何检测$ test为空?

不起作用:

$test -eq $null
-not $test

这确实有效,但感觉不正确:

$test.ToString() -eq ''

这是一个简化的示例,但是我的用例是我从使用REST-REST方法的REST api中获得的响应,某些属性作为空的psobjects返回。

3 个答案:

答案 0 :(得分:3)

这是 的最简单解决方案,它通过其 string表示形式来测试空(无属性)自定义对象([pscustomobject],但是您需要使用可扩展字符串(字符串插值,"..."而不是.ToString()来获得它:

# Returns $True, if custom object $test is empty, i.e. has no properties
-not "$test"

只有一个空(无属性)自定义对象会在可扩展字符串内字符串化为空字符串,并且在PowerShell中将空字符串强制为布尔值会生成$False,而任何非空字符串字符串产生$True

注意:-not $test.ToString() 应该是等效的,但是由于bug,当前(自PowerShell Core 6.1起)不相同。在存在该错误的情况下, any [pscustomobject]实例从.ToString()返回空字符串
另一个解决方法是使用.psobject.ToString()

上面的方法很方便,但是如果$test是一个具有许多属性的大对象,则它可能会很昂贵-尽管实际上这并不重要。


一种价格便宜但更模糊的解决方案是访问.psobject.Properties集合,该集合返回对象的属性定义:

# Returns $True, if $test has no properties
-not $test.psobject.Properties.GetEnumerator().MoveNext()

遗憾的是,.psobject.Properties集合没有.Count属性,因此可以通过.GetEnumerator()来解决。


关于您尝试过的事情

$test -eq $null

$test仍然是对象,即使它碰巧没有属性,并且根据定义,对象也永远不会$null

-not $test

PowerShell的隐式到布尔转换将任何 [pscustomobject]实例视为$True,无论它是否恰好具有属性。例如,[bool] ([pscustomobject] @{})产生$True

要查看其他数据类型如何强制转换为布尔值,请参见this answer

答案 1 :(得分:1)

可能价格更高,但晦涩;正在使用本机Get-Member cmdlet:

[Bool]($Test | Get-Member -MemberType NoteProperty)

请注意$Test不应为$Null(而不是空对象),否则将产生错误(如在{{1 }})。为避免这种情况,您还可以考虑使用:

$Null

答案 2 :(得分:0)

使用字符串测试并在比较的侧使用$ Var进行测试,以便将其强制为左侧的类型。您还可以使用下面的[string]方法进行测试... [咧嘴]

$Test = '{ }' | ConvertFrom-Json

$Test -eq $Null
$Null -eq $Test
$Test -eq ''
''
'' -eq $Test
[string]::IsNullOrEmpty($Test)
[string]::IsNullOrWhiteSpace($Test)

输出...

False
False
False

True
True
True