首页 > 解决方案 > Powershell - 将文件移动到名称部分匹配的现有文件夹

问题描述

我有一个文件夹,其中包含多个人将贡献的图像,并且我有多个其他人将使用其他内容创建的文件夹,文件夹名称将与文件名相似但不完全相同(请参见下面的示例)。我已经尝试编写一个 Powershell 脚本(我仍然有点绿色)将每个图像移动到其各自的文件夹但我碰壁了,我得到“无法将'System.Object []'转换为类型参数'Destination'需要'System.String'。不支持指定的方法。 “我尝试将目标转换为字符串,但在遍历文件夹列表时遇到问题。我在这里添加代码,希望有人能发现我在代码中犯的错误,并为我指明正确的方向。

$sourceFolder = Get-ChildItem 'C:\Example_Files_Folder' -Recurse -Filter *.png
$targetFolder = Get-ChildItem -Path 'C:\Example_Target_Folder' -Recurse -Directory

foreach ($file in $sourceFolder) {
        Where-Object { $targetFolder.Name -cin $sourceFolder.BaseName }
        move-Item -Path $file.FullName -Destination $targetFolder.FullName -WhatIf
        Write-Output "...copying $file" 
}


<# ### Folder Structure
▼sourceFolder #Root Folder containing files
├───►looking inside this folder.png
├───►you should be able to find.png
├───►quite a long list of files.png
├───►matching many folders names.png
└───►that exist inside other folders.png


▼targetFolder #Root Folder
├───▼subfolder01
│   └───►looking inside #this is a folder
├───▼subfolder02
|   └───▼subfolder002
|       └───▼subfolder0002
|           └───►you should be #also a folder
├───▼subfolder03
|   └───►quite a long #not a file, just a folder
├───▼subfolder04
|   └───►matching many folders #folder
├───▼subfolder05
|   └───►sometimes with no matching file name #yep, a folder
├───▼subfolder06
|   └─────►that exist within many folders #you get it
└───►subfolder07
### #>

标签: windowspowershell

解决方案


继续我的评论...您可以将其简化为这样说:

# Target folder tree
$targetFolders = Get-ChildItem -Path 'D:\Temp\Target' -Recurse -Directory
# Results
<#
    Directory: D:\Temp\Target


Mode          LastWriteTime Length Name    
----          ------------- ------ ----    
d-----  17-Feb-21     10:22        Book    
d-----  17-Feb-21     10:10        TextData


    Directory: D:\Temp\Target\Book


Mode          LastWriteTime Length Name
----          ------------- ------ ----
d-----  17-Feb-21     10:10        Date
#>

# Source folder files to move
Get-ChildItem 'D:\Temp' -Recurse -Filter '*.txt' | 
ForEach {
    ForEach ($targetFolder in $targetFolders)
    {
        If ($PSItem.BaseName -match $targetFolder.Name)
        {Move-Item -Path $PSItem.FullName -Destination $targetFolder.FullName -WhatIf}
    }
}
# Results
<#
What if: Performing the operation "Move File" on target "Item: D:\Temp\Book- Copy (2).txt Destination: D:\Temp\Target\Book\Book- Copy (2).txt".
....
What if: Performing the operation "Move File" on target "Item: D:\Temp\DateData.txt Destination: D:\Temp\Target\Book\Date\DateData.txt".
...
What if: Performing the operation "Move File" on target "Item: D:\Temp\TextData.txt Destination: D:\Temp\Target\TextData\TextData.txt".
#>

推荐阅读