将System.Collections.ArrayList转换为Powershell中的字符串

将System.Collections.ArrayList转换为Powershell中的字符串,powershell,formatting,Powershell,Formatting,我在powershell中有以下测试脚本,我面临的问题是我想将错误的详细信息存储在自定义对象或变量中作为字符串,现在错误变量的值是System.Collections.ArrayList类型 invoke-sqlcmd -ServerInstance "$sql" -inputfile $file -Database test -OutputSqlErrors $true -ConnectionTimeout 10 -ErrorAction Continue -Errorv

我在powershell中有以下测试脚本,我面临的问题是我想将错误的详细信息存储在自定义对象或变量中作为字符串,现在错误变量的值是System.Collections.ArrayList类型

invoke-sqlcmd -ServerInstance "$sql" -inputfile $file  -Database test -OutputSqlErrors $true -ConnectionTimeout 10 -ErrorAction Continue -Errorvariable err | Out-Null
现在,如果我跑的话,奇怪的是

$err | Get-Type
其类型为
System.Collections.ArrayList

如果我运行
write host$err
,它会正确打印错误,但会将
$err
的值分配给自定义对象,然后我会丢失该值,但会得到
'System.Collections.ArrayList'

$error_values += New-Object -TypeName psobject -Property @{ErrorMessage =$err}
现在运行
$error\u values |选择ErrorMessage返回System.Collections.ArrayList

我只需要它是一个简单的字符串,不确定这里有什么不正确。

    $arrayList = [System.Collections.ArrayList]::new()
    
    [void]$arrayList.Add("one")
    [void]$arrayList.Add("two")
    [void]$arrayList.Add("three")
    
    $msg = $arrayList -join ", "
    Write-Host $msg
    
  • 一般情况下,不要使用输出数据,因为那样不起作用仅用于仅显示输出;要输出数据,请使用或更好地使用PowerShell的隐式输出功能

    • 在您的情况下,
      $error\u values | select ErrorMessage
      本身不仅可以将感兴趣的信息作为数据输出,还可以产生有用的输出格式

    • 有关更多信息,请参阅

  • 具体而言,即使需要仅显示输出,也不要使用
    写入主机
    打印复杂对象的表示形式
    (笼统地说,是具有属性的对象)
    改用

    • $error\u values |选择ErrorMessage | Out Host
    • 顺便说一句:
      select
      ()调用实际上是一个no-op;我猜您的实际意思是
      $error\u values | select-ExpandProperty ErrorMessage
      -有关更多信息,请参阅
    • 写入主机
      不执行丰富的输出格式
      ,而PowerShell的默认显示格式和
      输出主机
      执行丰富的输出格式。由于
      Write Host
      使用简单的
      .ToString()
      字符串化,因此复杂对象通常会导致无效的表示-有关详细信息,请参阅
完整示例:

# Create a sample ArrayList, as returned by 
$err = [System.Collections.ArrayList] ('one', 'two')

# Construct a custom object ([pscustomobject]) with an .ErrorMessage
# property that contains the array list
$obj = [pscustomobject] @{ ErrorMessage = $err }

# !! Write-Host results in UNHELPFUL display:
# !! Note how instead of listing the *elements* of the ArrayList
# !! the *type name* ("System.Collections.ArrayList") is printed instead.
PS> Write-Host $obj
@{ErrorMessage=System.Collections.ArrayList}

# OK: Out-Host produces richly formatted *display-only* output.
PS> $obj | Out-Host

ErrorMessage
------------
{one, two}


# OK as well: *implicit* output, *as data* - same representation.
PS> $obj

ErrorMessage
------------
{one, two}
注意:对于元素不是复杂对象的集合的直接显示输出,
如果需要单行输出,
写入主机
会很有帮助,因为元素随后只是以空格连接:

$err=[System.Collections.ArrayList](“一”、“二”)
#确定收集非复杂对象以获得
#*单线*表示法。
#Out Host和implicit output在各自的行上打印每个元素。
PS>写入主机$err
12
您甚至可以使用
-Separator
来使用空格以外的分隔符:

PS>Write Host-Separator/'one','two'
一/二
当然,您也可以使用表达式来创建这样的字符串,使用操作符
-join
,这将允许您将输出用作数据:

PS>“一个”、“两个”连接“/”
一/二

可选读取:传递给
-ErrorVariable
的目标变量接收实例的原因:

在变量中收集流的输出的-以及所有常见的
-*变量
参数-总是返回带有收集的输出的实例,这在两个方面令人惊讶:

  • PowerShell通常使用
    [object[]]
    数组作为其默认收集数据类型

  • 此外,在
    -OutVariable
    的情况下,该行为与管道的直接输出不一致,其中命令的单个对象输出就是这样输出的,而不是包装在集合中,例如在这种情况下的
    ArrayList
    ;也就是说,尽管您希望以下两个命令是等效的,但它们不是:

    $out = Get-Date  
    # -> $out is a [datetime] instance.
    
    # !! -OutVariable *always* creates ArrayList.
    $null = Get-Date -OutVariable out 
    # -> $out is a *single-element ArrayList* containing a [datetime] instance.
    
有关这些不一致性的讨论,请参阅。

  • 一般情况下,不要使用输出数据,因为那样不起作用仅用于仅显示输出;要输出数据,请使用或更好地使用PowerShell的隐式输出功能

    • 在您的情况下,
      $error\u values | select ErrorMessage
      本身不仅可以将感兴趣的信息作为数据输出,还可以产生有用的输出格式

    • 有关更多信息,请参阅

  • 具体而言,即使需要仅显示输出,也不要使用
    写入主机
    打印复杂对象的表示形式
    (笼统地说,是具有属性的对象)
    改用

    • $error\u values |选择ErrorMessage | Out Host
    • 顺便说一句:
      select
      ()调用实际上是一个no-op;我猜您的实际意思是
      $error\u values | select-ExpandProperty ErrorMessage
      -有关更多信息,请参阅
    • 写入主机
      不执行丰富的输出格式
      ,而PowerShell的默认显示格式和
      输出主机
      执行丰富的输出格式。由于
      Write Host
      使用简单的
      .ToString()
      字符串化,因此复杂对象通常会导致无效的表示-有关详细信息,请参阅
完整示例:

# Create a sample ArrayList, as returned by 
$err = [System.Collections.ArrayList] ('one', 'two')

# Construct a custom object ([pscustomobject]) with an .ErrorMessage
# property that contains the array list
$obj = [pscustomobject] @{ ErrorMessage = $err }

# !! Write-Host results in UNHELPFUL display:
# !! Note how instead of listing the *elements* of the ArrayList
# !! the *type name* ("System.Collections.ArrayList") is printed instead.
PS> Write-Host $obj
@{ErrorMessage=System.Collections.ArrayList}

# OK: Out-Host produces richly formatted *display-only* output.
PS> $obj | Out-Host

ErrorMessage
------------
{one, two}


# OK as well: *implicit* output, *as data* - same representation.
PS> $obj

ErrorMessage
------------
{one, two}
注意:对于元素不是复杂对象的集合的直接显示输出,
如果需要单行输出,
写入主机
会很有帮助,因为元素随后只是以空格连接:

$err=[System.Collections.ArrayList](“一”、“二”)
#确定收集非复杂对象以获得
#*单线*表示法。
#Out Host和implicit output在各自的行上打印每个元素。
PS>写入主机$err
12
您甚至可以使用
-Separator