題 如何根據文件名將文件排序到文件夾中 - Windows CMD


如何使用CMD / PowerShell命令根據文件名將文件排序到文件夾中?

假設我有一個包含大量文件(超過20,000個文件)的文件夾,其中所有文件都具有相同的命名約定,例如:(注意模式)

t_1001_1801.png
t_1001_1802.png
t_1001_1803.png
...
t_1001_2112.png (last file starts with 't_1001_')
t_1002_1801.png
t_1002_1802.png
t_1002_1803.png
....
t_1002_2112.png
t_1003_1801.png
t_1003_1802.png
t_1003_1803.png
...
t_1214_2112.png (last file in folder)

我運行此CMD命令來創建文件夾列表:
for /l %i in (1001,1,1214) do md x%i 
這會創建一個文件夾列表,例如:

x1001
x1002
x1003
...
x1214

現在我想根據文件名將文件排序(移動)到文件夾中,例如:

- move the files t_1001_1801.png to t_1001_2112.png to the folder x1001.
- move the files t_1002_1801.png to t_1002_2112.png to the folder x1002.
...

我可以為此目的使用shell命令嗎?


5
2018-06-03 10:11


起源


查看PFrank文件重命名器,UI中非常強大的正則表達式批處理工具,預覽您的重命名/移動: www3.telus.net/pfrank - therobyouknow
沒試過這個,但怎麼樣 for /l %i in (1001,1,1024) do md x%i&mv t_%i_* x%i? - Neil


答案:


您只需要拆分FileName,獲取數字(如1001),將數字與文件夾進行比較,獲取正確的文件夾並移動文件:

# Folder where Files and Folders are located
$TopFolder = "C:\Install"

# Getting Folders and Files
$Folders = gci $TopFolder -OutVariable Files | ? { $_.PSisContainer }

# Loop over all Files with *.png extension
$Files | ? { $_.Extension -eq '.png' } | % {

    # Split FileName to get the number (like 1001)
    $num = ($_.Name -split "_")[1]

    # Get FolderName by reading out foldername (without 'x') and compare it to number
    $MoveTo = $Folders | ? { $_.Name.substring(1,($_.Name.length -1)) -eq $num }

    # If a folder was found, move file there. else print error
    if ($MoveTo)
    {
        Move-Item $_.FullName $MoveTo -Force
        Write-Host "Copied File $($_.Name) to $MoveTo"
    }
    else 
    { 
        Write-Host "Did not find folder x$($num) in $TopFolder" 
    }
}

7
2018-06-03 10:40



如何運行這個腳本?我創造了一個 .bat 文件並將腳本複製到它,但由於錯誤,腳本沒有執行。 - Gil Epshtain
@GilEpshtain這是一個PowerShell腳本。你需要創建一個 .ps1文件而不是 .bat。然後右鍵單擊 - 使用powershell運行 - SimonS
謝謝,它運作良好。我只需要稍微改變一下腳本,因為實際的文件名是 t_25_1001_1801.png (不像原來的問題)所以我做了這個改變 $num = ($_.Name -split "_")[2]。 - Gil Epshtain
大!在這種情況下,是[2]​​是正確的。 - SimonS


以下批次

  • 對要啟動的文件夾的更改
  • 通過所有* .png文件使用for命令進行迭代
  • 使用for / f將下劃線的名稱拆分為標記並使用 第2 第3個到
  • 檢查是否存在具有該編號的子文件夾x,如果沒有,則創建它
  • 最後將文件移動到子文件夾。

:: Q:\Test\2018\06\03\SU_1328200.cmd
@Echo off 
PushD "C:\Users\UserName\Pictures\"

For %%A in (t_*_*_*.png) do For /F "tokens=3delims=_" %%B in ("%%A") Do (
  If Not exist "x%%B" MD "x%%B"
  Move "%%A" "x%%B"
)
PopD

運行批處理後的樣本樹/ F.
(第二個令牌的第一個要求已過時)

> tree /F
├───x1001
│       t_1001_1801.png
│       t_1001_1802.png
│       t_1001_1803.png
│       t_1001_2112.png
│
├───x1002
│       t_1002_1801.png
│       t_1002_1802.png
│       t_1002_1803.png
│       t_1002_2112.png
│
├───x1003
│       t_1003_1801.png
│       t_1003_1802.png
│       t_1003_1803.png
│
└───x1214
        t_1214_2112.png

PowerShell腳本:

## Q:\Test\2018\06\03\SU_1328200.ps1
PushD  "C:\Users\UserName\Pictures\"
Get-ChildItem t_*_*_*.png |
  Where BaseName -match 't_\d{2}_(\d{4})_\d{4}'|
    Group {'x'+$Matches[1]}|
      ForEach{MD $_.Name;$_.Group|Move -Dest $_.Name}

5
2018-06-03 11:22



我試過你的CMD腳本,結果不如預期。創建的文件夾列表(x1001,x1002,...)和其他文件夾 - 使用根文件夾的名稱。比所有復製到具有“root”名稱的文件夾的文件。其余文件夾保持空白。由於錯誤,Shell腳本根本沒有運行。 - Gil Epshtain
嗯,我在沒有缺陷的情況下測試了我的ramdisk上的批次,你是否複製粘貼批次並更改了pushd之後的文件夾? - LotPings
謝謝你,這是我的錯。我需要做一個小改動。由於實際的文件名是 t_25_1001_1801.png(不像原來的問題)我需要做出這個改變 For /F "tokens=3delims=_"... - Gil Epshtain
改編我的批/腳本。 BTW我的PowerShell腳本比接受的答案更嚴格/錯誤/更快/更短,並創建必要的文件夾本身。 - LotPings


感謝@Neil,他的答案(在評論中),我只想將其作為其他人的答案發布。

for /l %i in (1001,1,1024) do md x%i&move t_%i_* x%i

說明:
- 在%i上循環從1001到1024(1是迭代步驟)
- 對於每次迭代,執行:
1.將目錄命名為x%i(x1001,x1002,...)。
2.將匹配正則表達式t_%i_ *(t_1001_1801)的文件移動到目錄x%i(剛創建的目錄)。


0
2018-06-04 09:26