我想要在PowerShell中等效于此代码
function containsElement () {
local e
for e in "${@:2}"; do [[ "$e" == "$1" ]] && return 0; done
return 1
}
请帮助我
答案 0 :(得分:2)
在PowerShell中,您不需要此功能,因为它带有collection-containment operators
-contains
和-in
(它们的区别仅在于数组是否位于LHS或RHS):
# Sample value to test.
$element = 1
# Sample array to test against.
$array = 5, 3, 2, 1, 6
# Test if the value is in the array.
$contains = $element -in $array
# output the value of $contains
$contains
如预期的那样,以上方法产生True
($true
的输出表示)。
注意事项:PowerShell与传统的shell不同,它具有基于.NET的 rich类型系统,这意味着(隐含的)相等比较可能并不总是按预期进行;简而言之,由于自动类型转换,比较中的操作数顺序很重要,因此'0xa' -in 10, 'other'
是$true
,而10 -in '0xa', 'other'
不是-请参阅{{3}的底部}。
如果确实需要使用作为各个参数 传递的数组元素来复制Bash函数:
function containsElement {
# Save the 1st argument passed and the remaining ones
# in separate local variables, using a destructuring assignment.
# $args is an automatic variable that contains the arguments
# passed as an array ([object[]]), akin to $@ in Bash.
$e, $arr = $args
# Test, and implicitly output the Boolean result.
$e -in $arr
}
# Sample call, equivalent of above.
containsElement 1 5 3 2 1 6
还请注意,PowerShell将布尔值作为 data (隐式或显式[bool]
值)进行通信,而不是通过不可见状态信息(退出代码)以POSIX的方式进行传递像Bash这样的外壳程序-有关更多信息,请参见this answer的底部。
$e
和$arr
是局部变量,因此是隐含的;如果您想使这一事实明确,则可以使用$local:e, $local:arr = $args
,但这绝对没有必要,因为 将分配给PowerShell中的变量隐式且始终不变
这不同于类似POSIX的外壳,后者的分配没有local
要么修改在父级范围内预先存在的变量;如果没有变量,则隐式在 top (脚本)范围内创建变量 [1] :
就像在POSIX一样的shell中一样,PowerShell中的后代作用域(子作用域及其子代...)会参见一个局部变量< / strong>。
ksh
[1] 除外)不同,PowerShell还提供了一种创建真正的本地变量的方法,即仅在定义范围内可见且可修改的变量,即通过 $private:
范围修饰符:$private:var = 'truly local'
[2] 。$private
的变量具有有效的行为,这是您期望的在 lexical 范围内的已编译编程语言(例如C#)中对局部变量的期望(相对于动态作用域内的脚本语言)。与类似POSIX的外壳不同,后代作用域不能通过不合格赋值 (或任何祖先作用域)修改调用者的本地变量变量。
$script:
和$scope:
范围说明符为祖先范围提供了显式访问权限 ,也可以通过-Scope
和Get-Variable
cmdlet的 Set-Variable
参数。有关PowerShell范围规则的更多信息,请参见this answer的底部。
[1]在类似POSIX的外壳中进行作用域演示
以下脚本可在bash
,dash
和zsh
中使用(bash
和dash
经常用作系统的默认Shell,{{1} }。
要使脚本在/bin/sh
中运行,您必须将ksh
关键字替换为local
,并使用typeset
关键字定义函数({{1 }}而不是function
),因为function a { ...
不了解a() { ...
,仅使用ksh
语法创建局部变量。
但是,与提到的其他类似POSIX的外壳不同,local
然后创建一个在后代作用域中看不到的真正本地变量,就像PowerShell的function
范围一样;换句话说:局部ksh
变量始终是 函数局部变量,而后代作用域从不看到它们。
$private:
这将产生以下内容:
ksh
[2]在PowerShell中#!/usr/bin/env bash
a() {
local var='1' # create local variable.
echo " calling scope before: [$var]"
b # call function b
echo " calling scope after: [$var]"
}
b() {
echo " child scope before: [$var]" # calling scope's var. is visible
var='1a' # modifies the *caller's* var.
local var=2
var='2a' # modifies the *local* var.
echo " child scope after: [$var]"
newvar='hi' # assigning to a variable that doesn't exist in any scope
# on the call stack creates it in the *top-level* scope.
}
# Call function a()
a
# var. created in b() without `local` is now visible.
echo "script scope: [$newvar]"
范围的演示
calling scope before: [1]
child scope before: [1]
child scope after: [2a]
calling scope after: [1a]
script scope: [hi]
也就是说,私有$private:
仅在外部# & { ... } executes ... in a child scope.
# Referencing a variable by itself implicitly outputs it (implicit `echo `).
PS> $var = 'outer'; & { $private:var = 'inner'; $var; & { $var } }
inner
outer
内部直接可见;嵌套的$var
再次看到了祖父母范围的{ ... }
。