更改特定列中的数据顺序

Change data order in a specific column

基于文件的 LastWriteTime 属性,我的脚本创建了一个带有自定义输出的 table 'File Age'。脚本工作正常,我的问题是特定列 'Age' 的输出,我无法像我那样设置顺序。 我已经尝试使用 cmdlet "Sort-Object -descending" 但没有成功,数据是随机放置的。 也许还有另一种自定义方式?

我想要的输出是这样的:

    Age
1 Day - 1 Week
1 Week - 1 Month
1 Month - 6 Months
6 Months - 1 Year
1 Year - 2 Years
< 2 Years

这是我的脚本:

$scan = gci c:\MyFolder
$scan | Add-Member ScriptProperty -Name FileAgeDays -Value {
            [int]((Get-Date) - ($this.LastWriteTime)).TotalDays}
$scan | Add-Member ScriptProperty -Name FileAge -Value {   

if ($this.FileAgeDays -le 7) {
    "1 Day - 1 Week"
}
elseif ($this.FileAgeDays -ge 7 -and $this.FileAgeDays -le 30) {
    "1 Week - 1 Month"
}
elseif ($this.FileAgeDays -ge 30 -and $this.FileAgeDays -le 180) {
    "1 Month - 6 Months"
}
elseif ($this.FileAgeDays -ge 180 -and $this.FileAgeDays -le 365) {
    "6 Months - 1 Year"
}
elseif ($this.FileAgeDays -ge 365 -and $this.FileAgeDays -le 730) {
    "1 Year - 2 Years"
}
elseif ($this.FileAgeDays -ge 730) {
    "< 2 Years"
}
}
$grp = $scan | ?{ ! $_.PSIsContainer } | Group FileAge | 
           Add-Member -MemberType ScriptProperty -Name SizeMB -Value {
           ($this.Group | Measure-Object Length -sum).Sum / 1MB} -PassThru

$age_frag = $grp | select`
 @{l='Size (MB)';e={"{0:n}" -f ($_.sizemb)}},`
 @{l='Age';e={$_.name}}, Count|
ConvertTo-Html -Fragment -As Table -PreContent "<br><H2><a name=a009>File Age</a></H2>"| 
Out-String

欢迎任何帮助。

您可以使用开关将文本值替换为可排序数据,例如。一个整数。

示例数据:

$data = [pscustomobject]@{ ID=1; FileAge="1 Day - 1 Week"},
[pscustomobject]@{ ID=4; FileAge="6 Months - 1 Year"},
[pscustomobject]@{ ID=2; FileAge="1 Week - 1 Month"},
[pscustomobject]@{ ID=5; FileAge="1 Year - 2 Years"},
[pscustomobject]@{ ID=6; FileAge="< 2 Years"},
[pscustomobject]@{ ID=3; FileAge="1 Month - 6 Months"}

$data

ID FileAge           
-- -------           
 1 1 Day - 1 Week    
 4 6 Months - 1 Year 
 2 1 Week - 1 Month  
 5 1 Year - 2 Years  
 6 < 2 Years         
 3 1 Month - 6 Months

现在,让我们来排序:

$data | Sort-Object {
    switch($_.FileAge) {
    "1 Day - 1 Week" { 1 }
    "1 Week - 1 Month" { 2 }
    "1 Month - 6 Months" { 3 }
    "6 Months - 1 Year" { 4 }
    "1 Year - 2 Years" { 5 }
    "< 2 Years" { 6 }
    }
}

ID FileAge           
-- -------           
 1 1 Day - 1 Week    
 2 1 Week - 1 Month  
 3 1 Month - 6 Months
 4 6 Months - 1 Year 
 5 1 Year - 2 Years  
 6 < 2 Years 

就个人而言,我会以不同的方式设计脚本。我会添加一个 FileAgeGroup-属性 和像 1,2,3.. 这样的整数值,按那个排序然后使用 Select-Object 生成用户友好的输出:

$data | Sort-Object ID | Select-Object @{n="FileAgeName";e={
    switch($_.ID) {
    1 { "1 Day - 1 Week" }
    2 { "1 Week - 1 Month" }
    3 { "1 Month - 6 Months" }
    4 { "6 Months - 1 Year" }
    5 { "1 Year - 2 Years" }
    6 { "< 2 Years" }
    }
}}

FileAgeName
-----------
1 Day - 1 Week
1 Week - 1 Month  
1 Month - 6 Months
6 Months - 1 Year 
1 Year - 2 Years  
< 2 Years

更新: 这是您的示例的未经测试的修改版本,我的第一个解决方案在其中实施(仅排序而不重写您的代码)。我在添加的代码上方添加了注释。

$scan = gci c:\MyFolder
$scan | Add-Member ScriptProperty -Name FileAgeDays -Value {
            [int]((Get-Date) - ($this.LastWriteTime)).TotalDays}
$scan | Add-Member ScriptProperty -Name FileAge -Value {   

if ($this.FileAgeDays -le 7) {
    "1 Day - 1 Week"
}
elseif ($this.FileAgeDays -ge 7 -and $this.FileAgeDays -le 30) {
    "1 Week - 1 Month"
}
elseif ($this.FileAgeDays -ge 30 -and $this.FileAgeDays -le 180) {
    "1 Month - 6 Months"
}
elseif ($this.FileAgeDays -ge 180 -and $this.FileAgeDays -le 365) {
    "6 Months - 1 Year"
}
elseif ($this.FileAgeDays -ge 365 -and $this.FileAgeDays -le 730) {
    "1 Year - 2 Years"
}
elseif ($this.FileAgeDays -ge 730) {
    "< 2 Years"
}
}
$grp = $scan | ?{ ! $_.PSIsContainer } | Group FileAge | 
           Add-Member -MemberType ScriptProperty -Name SizeMB -Value {
           ($this.Group | Measure-Object Length -sum).Sum / 1MB} -PassThru

#Scriptblock that can be used to sort by FileAge (Name-property in a Group)
$fileageSorting = {
    switch($_.Name) {
    "1 Day - 1 Week" { 1 }
    "1 Week - 1 Month" { 2 }
    "1 Month - 6 Months" { 3 }
    "6 Months - 1 Year" { 4 }
    "1 Year - 2 Years" { 5 }
    "< 2 Years" { 6 }
    }
}

$age_frag = $grp |
#Sorting
Sort-Object $fileageSorting |
select @{l='Size (MB)';e={"{0:n}" -f ($_.sizemb)}}, @{l='Age';e={$_.name}}, Count |
ConvertTo-Html -Fragment -As Table -PreContent "<br><H2><a name=a009>File Age</a></H2>"| 
Out-String