如果您想要一个元组列表,我建议您实际构建一个 tuples 列表:
$list = @()
$tuple1 = New-Object 'Tuple[String,String]' 'dog', 'cat'
$tuple2 = New-Object 'Tuple[String,String]' 'dog', 'horse'
$list += $tuple1
$list
# Output:
#
# Item1 Item2 Length
# ----- ----- ------
# dog cat 2
$list += $tuple2
$list
# Output:
#
# Item1 Item2 Length
# ----- ----- ------
# dog cat 2
# dog horse 2
请注意,在此示例中,$list 是一个常规数组,这意味着,正如@mklement0 在他的回答中指出的那样,使用+= 赋值运算符附加到它之后,将重新创建大小增加 1 的数组,将新的项放入新的空槽中,然后替换原来的数组。对于少量追加操作,这通常不是什么大问题,但随着追加操作数量的增加,性能影响变得显着。
使用ArrayList 而不是普通数组可以避免这个问题:
$list = New-Object Collections.ArrayList
$tuple1 = New-Object 'Tuple[String,String]' 'dog', 'cat'
$tuple2 = New-Object 'Tuple[String,String]' 'dog', 'horse'
$list.Add($tuple1) | Out-Null
$list
# Output:
#
# Item1 Item2 Length
# ----- ----- ------
# dog cat 2
$list.Add($tuple2) | Out-Null
$list
# Output:
#
# Item1 Item2 Length
# ----- ----- ------
# dog cat 2
# dog horse 2
ArrayList 对象的Add() 方法输出附加项目的索引。 Out-Null 抑制在大多数情况下不需要的输出。如果您想使用这些索引号,可以将它们收集到一个变量中,而不是丢弃它们 ($i = $list.Add($t1))。
如果你想避免一直指定新元组的类型,你可以将它包装成一个可重用的函数,如下所示:
function New-Tuple {
Param(
[Parameter(Mandatory=$true)]
[ValidateCount(2,2)]
[string[]]$Values
)
New-Object 'Tuple[String,String]' $Values
}
$tuple1 = New-Tuple 'dog', 'cat'
$tuple2 = New-Tuple 'dog', 'horse'
或者,以更通用的方式,像这样:
function New-Tuple {
Param(
[Parameter(
Mandatory=$true,
ValueFromPipeline=$true,
ValueFromPipelineByPropertyName=$true
)]
[ValidateCount(2,20)]
[array]$Values
)
Process {
$types = ($Values | ForEach-Object { $_.GetType().Name }) -join ','
New-Object "Tuple[$types]" $Values
}
}
$tuples = ('dog', 'cat'), ('dog', 'horse') | New-Tuple