假设我正在处理函数中的用户对象列表。
Function DoThings {
Process { $_.memberof).where{ $_ -match "Team_" }.foreach{ Remove-ADGroupMember $_ $_.samaccountname}
}#did things
问题在于,由于foreach循环正用于where的输出,因此我将自己限制为无法访问其余的对象属性。
我想循环遍历对象属性的子集,但我还需要能够从用户的属性访问其他信息以传递给cmdlet(例如用户名)。
到目前为止,我唯一能够想到的就是将$ _。samaccountname分配给一个临时变量,然后再调用它,但这样做不够优雅。
这样做有更干净的方法吗?
这可以被认为更优雅:
Function DoThings {
Process {
($_.memberof) |
Where-Object { $_ -match "Team_" } -PipelineVariable pipevar |
ForEach-Object { Remove-ADGroupMember $_ $pipevar.samaccountname}
}#did things
更多关于PipelineVariable
使用where()和foreach()方法可以指定参数。
Function DoThings {
Param ($user)
Process {
$_.memberof.Where{
$_ -match "Team_" }.foreach{
Remove-ADGroupMember $_ $user.samaccountname}
}
}#did things
通过将输入指定为参数,可以使用参数名称访问初始对象。
DoThings $Userlist
或者,为了保持管道可访问性,您可以将该函数转换为高级函数,以允许参数显式接受管道输入。
Function DoThings {
[cmdletbinding()]
param([Parameter(ValueFromPipeline = $true)]$user)
Process {
$_.memberof.where{
$_ -match "Team_" }.foreach{
Remove-ADGroupMember $_ $user.samaccountname}
}
}#did things
然后将工作
$Userlist DoThings
基本功能将接受管道输入,但只能通过自动变量$ _访问。在我的测试中使用自动变量$ input可以访问初始对象属性,但看起来每个函数只能使用一次。
而不是为临时变量赋值,使用高级函数的功能更加优雅。
相同的技术可以与ForEach-Object和Where-Object cmdlet一起使用,而无需创建新变量。