代码之家  ›  专栏  ›  技术社区  ›  esac

如何在列中列出的列表中按字母顺序排序?

  •  5
  • esac  · 技术社区  · 14 年前

    结果是 Get-ChildItem Write-Host 然后我把它列成这样:

    PerfLogs  Program Files  Program Files (x86)  Python31  Temp  Users  Windows
    

    但是,假设我知道我希望它拆分成x列,我希望输出如下所示:

    PerfLogs                  Python31     Windows
    Program Files             Temp
    Program Files (x86)       Users
    

    如您所见,它先在列中列出它,然后在列中列出它。

    知道怎么得到这样的输出吗?理想情况下,它将使用屏幕上最多的列,每个列的名称都与左边对齐。

    function color-ls
    {
        dir $args | Format-High -Print {    
            $item = $args
            $fore = $host.UI.RawUI.ForegroundColor        
            $host.UI.RawUI.ForegroundColor = .{     
                if ($item[1].psIsContainer) {'Blue'}
                elseif ($item[1].Extension -match '\.(exe|bat|cmd|ps1|psm1|vbs|rb|reg|dll|o|lib)') {'Red'}
                elseif ($item[1].Extension -match '\.(zip|tar|gz|rar)') {'Yellow'}
                elseif ($item[1].Extension -match '\.(py|pl|cs|rb|h|cpp)') {'Cyan'}
                elseif ($item[1].Extension -match '\.(txt|cfg|conf|ini|csv|log|xml)') {'Green'}
                else {$fore}
            }
            write-host $args[0] -NoNewLine
            $host.UI.RawUI.ForegroundColor = $fore
        }
    }
    

    输出:

    http://dl.dropbox.com/u/2809/lscolor.png

    1 回复  |  直到 14 年前
        1
  •  6
  •   Roman Kuzmin    13 年前

    这是一个有趣的想法和任务。

    脚本格式-High.ps1:

    <#
    .SYNOPSIS
        Formats input by columns using maximum suitable column number.
    
    .DESCRIPTION
        Format-High prints the specified property, expression, or string
        representation of input objects filling the table by columns.
    
        It is named in contrast to Format-Wide which prints by rows.
    
    .EXAMPLE
        # just items
        ls c:\windows | Format-High
    
        # ditto in colors based on PSIsContainer
        ls c:\windows | Format-High -Print {$c = if ($args[1].PSIsContainer) {'yellow'} else {'white'}; Write-Host $args[0] -ForegroundColor $c -NoNewline}
    
        # just processes, not good
        ps | Format-High
    
        # process names, much better
        ps | Format-High Name
    
        # custom expression and width
        ps | Format-High {$_.Name + ':' + $_.WS} 70
    
        # process names in colors based on working sets
        ps | Format-High Name 70 {$c = if ($args[1].WS -gt 10mb) {'red'} else {'green'}; Write-Host $args[0] -ForegroundColor $c -NoNewline}
    #>
    
    param
    (
        [object]$Property,
        [int]$Width = $Host.UI.RawUI.WindowSize.Width - 1,
        [scriptblock]$Print = { Write-Host $args[0] -NoNewline },
        [object[]]$InputObject
    )
    
    # process the input, get strings to format
    if ($InputObject -eq $null) { $InputObject = @($input) }
    if ($Property -is [string]) { $strings = $InputObject | Select-Object -ExpandProperty $Property }
    elseif ($Property -is [scriptblock]) { $strings = $InputObject | ForEach-Object $Property }
    else { $strings = $InputObject }
    $strings = @(foreach($_ in $strings) { "$_" })
    
    # pass 1: find the maximum column number
    $nbest = 1
    $bestwidths = @($Width)
    for($ncolumn = 2; ; ++$ncolumn) {
        $nrow = [Math]::Ceiling($strings.Count / $ncolumn)
        $widths = @(
            for($s = 0; $s -lt $strings.Count; $s += $nrow) {
                $e = [Math]::Min($strings.Count, $s + $nrow)
                ($strings[$s .. ($e - 1)] | Measure-Object -Maximum Length).Maximum + 1
            }
        )
        if (($widths | Measure-Object -Sum).Sum -gt $Width) {
            break
        }
        $bestwidths = $widths
        $nbest = $ncolumn
        if ($nrow -le 1) {
            break
        }
    }
    
    # pass 2: print strings
    $nrow = [Math]::Ceiling($strings.Count / $nbest)
    for($r = 0; $r -lt $nrow; ++$r) {
        for($c = 0; $c -lt $nbest; ++$c) {
            $i = $c * $nrow + $r
            if ($i -lt $strings.Count) {
                & $Print ($strings[$i].PadRight($bestwidths[$c])) $InputObject[$i]
            }
        }
        & $Print "`r`n"
    }