将文件夹移动到按年份排序的其他文件夹

Move folders to other folders sorted by year

我有这些文件

Andromeda (2009)
Mrtik.2004.[director cut]
Jvengers 1999

要按字母顺序移动和排序文件夹,我可以使用

Get-ChildItem -Directory -Path ??* |
  Move-Item -Destination { 
    # Determine the target dir - the input dir's first letter -
    # ensure that it exists, and output it.
    New-Item -Type Directory -Force (Join-Path $_.Parent.FullName $_.Name[0])
  } 

此代码创建 AJM 文件夹,然后将它们移动到此方式

  A 
  | ---> Andromeda (2009)

  J
  | ---> Jvengers 1999
  
  M 
  | ---> Mrtik.2004.[director cut]
  
  

但我更喜欢另一种情况

1999
  | ---> Jvengers 1999
  
2004 
  | ---> Mrtik.2004.[director cut]

2009 
  | ---> Andromeda (2009)

有什么想法吗?

一种方法是使用 Group-Object 按匹配模式(在本例中为 4 位数字 - \d{4})对所有文件夹进行分组,然后您可以遍历这些组并在根据需要创建目标文件夹并将文件夹组移至该文件夹。

Get-ChildItem -Directory | Group-Object { [regex]::Match($_.Name, '\d{4}').Value } |
ForEach-Object {
    # if the pattern was not matched exclude this group
    # this is a folder without a year
    if(-not $_.Name) { return }

    $destination = Join-Path -Path $_.Group[0].Parent -ChildPath $_.Name
    if(-not (Test-Path $destination)) {
        $destination = New-Item $destination -ItemType Directory
    }
    
    # need to exclude those folders from the group that are our destination
    # without this you can trriger the following exception:
    # `Destination path cannot be a subdirectory of the source ...`
    $folders = $_.Group.Where{ $_.FullName -ne $destination }
    # if there are no folders to move, go to the next group
    if(-not $folders) { return }
    Move-Item -LiteralPath $folders -Destination $destination
}