如何在Powershell中调用带有数组参数的函数?

时间:2014-03-05 14:55:47

标签: arrays powershell

在名为arrays.ps1

的文件中考虑此脚本
Function CallMe
{
    param($arg1, $arg2)
    Write-Host "`$arg1 is $arg1"
    Write-Host "`$arg2 is $arg2"    
}

$args = "a","b"
CallMe $args

输出:

PS C:\Users\Moomin\Documents> .\arrays.ps1
$arg1 is a b
$arg2 is

如果我修改它,那么最后一行是

CallMe $args.Split(" ")

我得到相同的输出。如何将数组传递给函数并将数组元素拆分为参数?

更新

这更接近我正在做的事情:

Function CallMe
{
    param($y, $z)
    Write-Host "`$y is $y"
    Write-Host "`$z is $z"

}

Function DoSomething
{
    param($x)
    Write-Host "This function only uses one arg: $x"
}

Function DoSomethingElse
{
    Write-Host "This function does not take any arguments"   
}


$funcCalls = (
    ("DoSomething", "c"),
    ("CallMe", ("a","b")),
    ("DoSomethingElse", '')
    )


foreach ($func in $funcCalls) {
    Write-Host "Executing function $($func[0]) with arguments `"$($func[1])`""
    & $func[0] $func[1]
}

如果我运行它,那就是输出:

PS C:\Users\Moomin\Documents> .\arrays.ps1
Executing function DoSomething with arguments "c"
This function only uses one arg:
Executing function CallMe with arguments "a b"
$y is a b
$z is
Executing function DoSomethingElse with arguments ""
This function does not take any arguments

3 个答案:

答案 0 :(得分:6)

您可以使用@'展开'数组,将每个元素作为参数传递给函数。

$array = @('a', 'b')
CallMe @array

从更新的示例中,最好将函数存储为ScriptBlocks而不是字符串,并使用.Invoke()来执行。

$funcCalls = (
    ({DoSomething @args}, "c"),
    ({CallMe @args}, ("a","b")),
    ({DoSomethingElse @args}, '')
    )

foreach ($func in $funcCalls) {
    Write-Host "Executing function {$($func[0])} with arguments `"$($func[1])`""
    $func[0].Invoke($func[1])
}

请注意,参数数组会传递给自动变量$args,该变量会被映射为@args

编辑:

如果您从无法将其存储为ScriptBlocks的源中读取函数,则可以使用[scriptblock]::Create()将字符串转换为ScriptBlock。

$funcCalls = (
    ('DoSomething @args', "c"),
    ('CallMe @args', ("a","b")),
    ('DoSomethingElse @args', '')
    )

foreach ($func in $funcCalls) {
    Write-Host "Executing function {$($func[0])} with arguments `"$($func[1])`""
    $script = [scriptblock]::Create($func[0])
    $script.Invoke($func[1])
}

答案 1 :(得分:2)

您遇到了这种情况,因为数组内容"a",b"$arg1定义为$Args的值,因为您没有明确地将其分配给您定义的任何一个参数。除非你绝对打算,否则我也会谨慎使用Function CallMe { # Foreach array iterate, write to host on a new line. $Args | % { Write-Host "Iterate content: $_" } } ,因为它是powershell中的positionally,它包含一系列未声明的参数值,您可以将这些参数值传递给函数。你现在没有在你的实际功能中使用它,但变量名称足够接近,可以指出它。

示例:

PS C:\> CallMe "a","b" "a" "b"
Iterate content: a b
Iterate content: a
Iterate content: b

输出:

$Args

如果我们将其应用于任何其他集合,那么迭代Function CallMe { param ( [string[]]$array = "" ) # Foreach array iterate, write to host on a new line. $array | % { Write-Host "Iterate content: $_" } } 的策略应该适用于您的情况,只要您“分割”数组内容的目标是单独处理每个迭代。

示例:

PS C:\> CallMe "a","b"
Iterate content: a
Iterate content: b

输出:

{{1}}

答案 2 :(得分:0)

对于'CallMe'函数,不要在参数之间使用逗号(使用空格): $ funcCalls =(     (“DoSomething”,“c”),     (“CallMe”,(“a”“b”)),     (“DoSomethingElse”,'')     )