如何控制PowerShell脚本块的范围

如何控制PowerShell脚本块的范围,powershell,closures,scriptblock,Powershell,Closures,Scriptblock,我在PowerShell中编写了一个函数: function replace([string] $name,[scriptblock] $action) { Write-Host "Replacing $name" $_ = $name $action.Invoke() } 并将用作: $name = "tick" replace $agentPath\conf\buildAgent.dist.properties { (cat templates\buildA

我在PowerShell中编写了一个函数:

function replace([string] $name,[scriptblock] $action) {
    Write-Host "Replacing $name"
    $_ = $name
    $action.Invoke()
}
并将用作:

$name = "tick"
replace $agentPath\conf\buildAgent.dist.properties {
    (cat templates\buildAgent.dist.properties.tpl) `
        -replace '@@serverurl@@', 'http:/localhost:8080/teamcity' `
        -replace '@@name@@', $name `
        > $_
}
但是,我发现在scriptblock中,变量
$name
replace
函数中的
$name
参数覆盖


是否有一种执行脚本块的方法,以便只将变量
$\ucode>添加到脚本块的作用域中,而不将其他变量添加到脚本块的作用域中?

您可以在脚本块中使用
$global:
前缀作为
$name
变量:


您可以在scriptblock中为
$name
变量使用
$global:
前缀:


在回答问题之前,我先声明powershell只适用于虐待狂。诀窍在于,如果将函数放入模块中,局部变量将变为私有变量,而不会传递给脚本块。然后,要传入
$\uu
变量,您必须再跳几圈

gv'.
获取powershell变量
$.
,并通过
InvokeWithContext
将其传递到上下文

现在我知道的比我想知道的更多:|

New-Module {
    function replace([string] $name,[scriptblock] $action) {
        Write-Host "Replacing $name"
        $_ = $name
        $action.InvokeWithContext(@{}, (gv '_'))
    }
}
和以前一样

$name = "tick"
replace $agentPath\conf\buildAgent.dist.properties {
    (cat templates\buildAgent.dist.properties.tpl) `
        -replace '@@serverurl@@', 'http:/localhost:8080/teamcity' `
        -replace '@@name@@', $name `
        > $_
}

在回答问题之前,我先声明powershell只适用于虐待狂。诀窍在于,如果将函数放入模块中,局部变量将变为私有变量,而不会传递给脚本块。然后,要传入
$\uu
变量,您必须再跳几圈

gv'.
获取powershell变量
$.
,并通过
InvokeWithContext
将其传递到上下文

现在我知道的比我想知道的更多:|

New-Module {
    function replace([string] $name,[scriptblock] $action) {
        Write-Host "Replacing $name"
        $_ = $name
        $action.InvokeWithContext(@{}, (gv '_'))
    }
}
和以前一样

$name = "tick"
replace $agentPath\conf\buildAgent.dist.properties {
    (cat templates\buildAgent.dist.properties.tpl) `
        -replace '@@serverurl@@', 'http:/localhost:8080/teamcity' `
        -replace '@@name@@', $name `
        > $_
}

我可以,但这是要求我或其他开发人员忘记某一天,而问题会在将来随机出现。我希望另一端会有某种解决方案,脚本块的调用者很礼貌,不会将所有的局部变量都注入作用域。我找到了一种方法。它确实很难看:)看我的答案。它看起来很难看,但我同意对其他使用该功能的开发人员来说更好。我可以,但这是在要求我或其他开发人员忘记某一天,而问题会在将来随机出现。我希望另一端会有某种解决方案,脚本块的调用者很礼貌,不会将所有的局部变量都注入作用域。我找到了一种方法。它确实很难看:)看我的答案。它看起来很难看,但我同意对其他使用该功能的开发人员来说更好。