将管道对象块化为数组的PowerShell函数无法获得正确的结果

时间:2014-01-01 17:47:23

标签: powershell pipeline

我正在学习PowerShell并尝试编写一个函数来将管道对象块化为数组。如果用户提供了一个脚本块$ Process,该函数会将scriptblock应用于每个管道对象,然后再将它们发送到管道(在下面的代码中尚未实现)。因此,假设将参数$ InputObject作为1, 2, 3, 4, 5并将$ ElementsPerChunk作为2,则该函数应返回3个数组@(1, 2), @(3, 4), @(5)。以下是我目前的代码:

function Chunk-Object
{
    [CmdletBinding()]
    Param (
        [Parameter(Mandatory = $true,
                   ValueFromPipeline = $true,
                   ValueFromPipelineByPropertyName = $true)] [object[]] $InputObject,
        [Parameter()] [scriptblock] $Process,
        [Parameter()] [int] $ElementsPerChunk
    )

    Begin {
        $cache = @();
        $index = 0;
    }
    Process {
        if($cache.Length -eq $ElementsPerChunk) {
            # if we collected $ElementsPerChunk elements in an array, sent it out to the pipe line
            Write-Output $cache;

            # Then we add the current pipe line object to the array and set the $index as 1
            $cache = @($_);
            $index = 1;
        }
        else {
            $cache += $_;
            $index++;
        }

    }
    End {
        # Here we check if there are anything still in $cache, if so, just sent out it to pipe line
        if($cache) {
            Write-Output $cache;
        }
    }
}


echo 1 2 3 4 5 6 7 | Chunk-Object -ElementsPerChunk 2;
Write-Host "=============================================================================";
(echo 1 2 3 4 5 6 7 | Chunk-Object -ElementsPerChunk 2).gettype();
Write-Host "=============================================================================";
(echo 1 2 3 4 5 6 7 | Chunk-Object -ElementsPerChunk 2).length;

当我执行代码时,我得到了:

1
2
3
4
5
6
7
=============================================================================

IsPublic IsSerial Name                                     BaseType                                                                                                                                          
-------- -------- ----                                     --------                                                                                                                                          
True     True     Object[]                                 System.Array                                                                                                                                      
=============================================================================
7

如您所见,结果是一个数组并包含7个元素。我对结果的期望是4个元素:@(1, 2), @(3, 4), @(5, 6), @(7)。任何人都可以帮我检查我的代码并解释问题吗?感谢。

1 个答案:

答案 0 :(得分:2)

问题在于,当您从进程块返回时,管道正在“展开”每个块数组。尝试在返回数组的Process块中进行此更改:

Write-Output (,$cache);

这将使返回成为一个2D数组,然后它将“展开”为单个数组而不是单个数组元素。