1

我制作了一个 Powershell 脚本,它对字符串数组执行 foreach 并仅收集其中的一些信息。这是代码:

begin {
    $IMAGELIST = @(
    "IMAGE Srv01 something something something Srv01_999888777 something"
    "FRAG 1 something something"
    "FRAG 2 something something"
    )
}   

process {
    foreach ($LINE in $IMAGELIST) {
        if ($LINE.StartsWith("IMAGE")) {
            $IMAGELINE = $LINE.split()
            $BKP_OBJ = [pscustomobject]@{
                Server=$IMAGELINE[1]
                Id=$IMAGELINE[5]
            }
        }

        elseif ($LINE.StartsWith("FRAG")) {
            $FRAGLINE = $LINE.split()
            $BKP_OBJ | Add-Member -Force @{
                CopyNumber = $FRAGLINE[1]
            }
            Write-Output -InputObject $BKP_OBJ
        }
    }
}

当我运行脚本时,我有两个具有不同 CopyNumber 值的对象的输出(预期结果):

PS C:\Users\db> .\BkpScript.ps1
Server            : Srv01
Id                : Srv01_999888777
CopyNumber        : 1

Server            : Srv01
Id                : Srv01_999888777
CopyNumber        : 2

如果我尝试将输出存储在一个变量中,我有相同的 CopyNumber(不是预期的结果):

PS C:\Users\db> $myvar = .\BkpScript.ps1
PS C:\Users\db> $myvar
Server            : Srv01
Id                : Srv01_999888777
CopyNumber        : 2

Server            : Srv01
Id                : Srv01_999888777
CopyNumber        : 2

我究竟做错了什么?

4

3 回答 3

1

此代码将在输出/管道时创建一个新对象:

begin {
    $IMAGELIST = @(
    "IMAGE Srv01 something something something Srv01_999888777 something"
    "FRAG 1 something something"
    "FRAG 2 something something"
    )
}   

process {
    $Server = ""
    $Id = ""
    $CopyNumber = 0
    foreach ($LINE in $IMAGELIST) {
        if ($LINE.StartsWith("IMAGE")) {
            $IMAGELINE = $LINE.split()
            $Server=$IMAGELINE[1]
            $Id=$IMAGELINE[5]
        } elseif ($LINE.StartsWith("FRAG")) {
            $FRAGLINE = $LINE.split()
            $CopyNumber = $FRAGLINE[1]
            Select-Object @{n='Server'; e={$Server}}, @{n='Id'; e={$Id}}, @{n='CopyNumber'; e={$CopyNumber}} -InputObject ''
        }
    }
}

输出看起来像您在问题中所期望的那样:

PS C:\Users\db\Desktop> .\test.ps1

Server Id              CopyNumber
------ --              ----------
Srv01  Srv01_999888777 1
Srv01  Srv01_999888777 2


PS C:\Users\db\Desktop> $myvar = .\test.ps1
PS C:\Users\db\Desktop> $myvar

Server Id              CopyNumber
------ --              ----------
Srv01  Srv01_999888777 1
Srv01  Srv01_999888777 2
于 2020-04-08T15:27:07.830 回答
0

我猜你想要这样的东西?

begin {
    $BKP_OBJ = $null
    $IMAGELIST = @(
    "IMAGE Srv01 something something something Srv01_999888777 something",
    "FRAG 1 something something",
    "FRAG 2 something something"
    )
}   

process {
    $Ximglist = @()
    $Xfrglist = @()
    foreach ($LINE in $IMAGELIST) {
        if ($LINE.StartsWith("IMAGE")) {
            $Ximglist += $LINE
        }
        elseif ($LINE.StartsWith("FRAG")) {
            $Xfrglist += $LINE
        }
    }
    foreach ($Ximg in $Ximglist) {
        $Xfrglist | % {($_.split())[1]} | % {$BKP_OBJ = [pscustomobject]@{
                    Server= ($Ximg.Split())[1]
                    Id= ($Ximg.Split())[5]
                    CopyNumber=$_
                }; 
                Write-Output $BKP_OBJ}
        }
    }
于 2020-04-08T12:40:06.923 回答
0

你只制作一个对象,你修改和输出两次。在显示任何输出之前,赋值语句首先使其完成。两个输出的指针相同。(.\BkpScript) 会做同样的事情。

cat myscript.ps1

$a = [pscustomobject]@{name='Joe'}
$a
$a.name = 'John'
$a


./myscript      

name
----
Joe
John


(./myscript)  # or ./myscript | sort

name
----
John
John
于 2020-04-08T15:23:24.063 回答