gpt4 book ai didi

powershell - 对象输出的奇怪延迟后跟开始 sleep (或直到脚本结束)

转载 作者:行者123 更新时间:2023-12-02 22:28:56 27 4
gpt4 key购买 nike

出于某种原因,对象在 sleep 命令完成之前不会输出。

[pscustomobject]@{message = 'hi'}; sleep 5

这是另一个例子。在循环完成之前您不会看到输出。
foreach ($i in 1..60) { 
if ($i -eq 1) { [pscustomobject]@{message = $i} }
sleep 1
}

我猜你必须至少输出 2 个对象才能看到任何东西? ¯\_(ツ)_/¯ 15 秒后,您会看到两个对象。
foreach ($i in 1..60) {
if ($i -eq 1 -or $i -eq 15) { [pscustomobject]@{message = $i} }
sleep 1
}

或者输出足够的属性(> 4)来隐式调用格式列表而不是格式表。格式表是问题所在。这马上就出来了。
[pscustomobject]@{a=1; b=2; c=3; d=4; e=5}; sleep 10

我想知道是否可以添加格式表的参数,如 -NoWait .

具有包含列宽的格式文件的已知对象类型不存在此问题。
foreach ($i in 1..60) { 
if ($i -eq 1) { get-process powershell }
sleep 1
}

或默认为自定义格式的对象:
foreach ($i in 1..60) { 
if ($i -eq 1) { get-date }
sleep 1
}

最佳答案

tl;博士

  • 如果命令的输出导致自动表格显示(隐式 Format-Table ),则显示输出可能会延迟最多 300 毫秒。 (请参阅下文了解原因和时间),这可能会产生两种意想不到的效果:
  • 在问题中,在延迟过去之前提交的后续 Start-Sleep 进一步延迟输出(至少) sleep 持续时间 - 它有效地暂停了完成 300 毫秒。等待。
  • 后续的 Write-HostOut-Host 调用可能会产生意外首先出现的输出。
  • 您可以通过将命令明确传递到 Out-HostFormat-Table(或任何其他 Format-* cmdlet)来强制同步显示输出。
  • 但是,这样做意味着仅生成用于显示的输出,这意味着您无法(有意义地)捕获或中继命令的输出。
  • # The Out-Host forces instant display, before sleeping starts.
    # However, use of Out-Host means you can't capture the output.
    [pscustomobject] @{message = 'hi'} | Out-Host; sleep 5

    该行为由臭名昭著的 PSv5+ asynchronous behavior of implicitly applied Format-Table output 解释:对于具有 4 个或更少属性的没有预定义格式数据的数据类型(这是自动选择表显示的内容),它等待最多 300 毫秒。在显示输出之前,努力确定合适的列宽。

    如果您在该时间段过去之前使用 Start-Sleep,则只要您在 sleep ,您就会暂停等待。

    碰巧不触发隐式 Format-Table 格式的输出对象不受影响,但是:
    # Immediate output, before sleeping ends:

    # Out-of-band formatting of a .NET primitive.
    PS> 1; Start-Sleep 5

    # Implicit Format-*List* formatting due to having 5+ properties.
    PS> [pscustomobject]@{a=1; b=2; c=3; d=4; e=5}; sleep 10

    相比之下,由于您的命令的输出是一个只有 1 个属性的对象,并且其类型 ( [pscustomobject] ) 没有与之关联的预定义格式数据,因此它会触发隐式 Format-Table 格式,因此会出现问题。

    简而言之:以下命令输出受到影响 ,因为它们选择隐式 Format-Table 输出同时缺少预定义的列宽,因此需要延迟:
  • 类型恰好具有 4 个或更少属性的对象
  • 如果这些类型有 没有关联的预定义格式数据 (参见 about_Format.ps1xml ),这对于 [pscustomobject] 实例通常是正确的。
  • 此外,但不太常见的是,格式数据默认为表格 View 但没有预定义列宽的类型也会受到影响(例如,System.Guid 输出的 New-Guid 类型实例)。

  • 没有格式化数据且具有 5 个或更多属性的类型默认为隐式应用 Format-List ,其中,由于逐行输出,无需确定有用的列宽,因此没有延迟。

    请注意,这只是一个显示问题,如果命令被捕获或发送到管道,数据会立即输出(尽管该命令在 Start-Sleep 时间段过去之前不会整体完成):
    # The ForEach-Object command's script block receives the [pscustomobject]
    # instance right away (and itself prints it *immediately* to the display,
    # due to outputting a *string* (which never triggers the asynchronous behavior).
    & { [pscustomobject]@{message = 'hi'}; sleep 5 } | ForEach-Object { "[$_]" }

    虽然有多种方法可以强制同步(立即)显示输出,但它们都改变了命令的基本行为:
    # Piping to Out-Host:
    # Directly prints to the *display* (host).
    # No way for a caller to capture the result or for processing
    # the result in a pipeline.
    [pscustomobject]@{message = 'hi'} | Out-Host; sleep 5

    # Using Write-Host:
    # Prints directly to the *display* (host) by default.
    # While it *is* possible to capture the result via output stream 6.
    # the information stream (6> file.txt), that output:
    # * is invariably converted to *strings*
    # * and the string representation does *not* use the friendly default
    # output formatting; instead, the objects are stringified with simple
    # [psobject.].ToString() calls, which results in a much less friendly
    # representation.
    Write-Host ([pscustomobject]@{message = 'hi'}); sleep 5

    # Piping to a Format-* cmdlet explicitly:
    # While this does write to the success-output stream (stream number 1),
    # as the command would by default, what is written isn't the original
    # objects, but *formatting instructions*, which are useless for further
    # programmatic processing.
    # However, for redirecting the output to a file with Out-File or >
    # this makes no difference, because they convert the formatting instructions
    # to the strings you would see on the screen by default.
    # By contrast, using Set-Content or any other cmdlet that expects actual data
    # would not work meaningfully.
    [pscustomobject]@{message = 'hi'} | Format-Table; sleep 5

    关于powershell - 对象输出的奇怪延迟后跟开始 sleep (或直到脚本结束),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59330539/

    27 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com