简而言之,我有大约30个名为Document(s)的文件夹和一个数字,所以
文档
文档2
…
文件30
这些文件夹下面可能是一个客户端文件夹(可以在多个文档文件夹中)。当我归档这些数据时,我需要找到非空文件夹,将Robocopy复制到另一个位置。
此脚本将在所有文档文件夹中搜索正确的客户端名称,然后检查其下面的文件夹是否为空。但速度很慢。真的很慢。有什么加快速度的建议吗?
我不确定PS是否统计了所有文件,或者只是检查计数是否大于0并继续前进。我检查根文件夹大小是否大于0的其他尝试也没有很好地运行;他们似乎还想对每个文件/文件夹进行计数/求和,而我只需要知道什么是>0字节。
感谢
$filePath = "\pathtoDocument**"
$folderName = "HelloWorld"
Get-ChildItem -Force $filePath -ErrorAction SilentlyContinue |
Where-Object { ($_.PSIsContainer -eq $true) `
-and ( $_.Name -like "*$folderName*") `
-and (Get-ChildItem -Path $_.FullName -Recurse |
Where-Object {$_.PSIsContainer -eq $True `
-and $_.GetFileSystemInfos().Count -gt 0 }) } |
Select-Object FullName | format-Table * -AutoSize
更新
对于@TheMadTechnician:
对于任何具有非空子目录的内容,返回"根"文件夹路径是否正确?例如
\\路径\to\Documents3\HelloWorld
\\路径\to\Documents19\HelloWorld
\\路径\to\Documents20\HelloWorld
$FolderName = "HelloWorld"
$FilePath = "\pathtoDocument*$FolderName"
$EmptyPaths = @()
ForEach($Folder in (Get-ChildItem $FilePath -Directory)){
If((Get-ChildItem "$($Folder.FullName)*").Count -gt 0){Continue}
Get-ChildItem $Folder -Recurse -File|ForEach{break}
$EmptyPaths += $Folder |
Select-Object FullName | format-Table * -AutoSize
}
如果允许文件系统提供程序过滤结果,我认为您将看到速度的大幅提高。然后,您可以使用ForEach循环,检查每个文件夹的根目录中的文件(如果根目录中有文件,则无需递归,我们可以将continue
搜索到下一个文件夹),如果没有根文件,则递归搜索文件,并在找到的第一个文件上搜索break
,这将移动到下一根文件夹:
$FolderName = "HelloWorld"
$FilePath = "\pathtoDocument*$FolderName"
$EmptyPaths = @()
$AllRootPaths = Get-ChildItem $FilePath -Directory
ForEach($Folder in $AllRootPaths){
If((Get-ChildItem "$($Folder.FullName)*").Count -gt 0){Continue}
Get-ChildItem $Folder -Recurse -File|ForEach{break}
$EmptyPaths += $Folder
}
$AllRootPaths | Where{$_ -notin $EmptyPaths} | Select -Expand FullName
我打赌这会大大加快你的成绩。在托管文件的服务器上的会话中运行这个程序,这样你就不必执行UNC路径了,速度会更快,因为它都是本地的,但我意识到这通常不是一个选项。
由于break
的行为,我使用了ForEach循环,而不是内联的ForEach对象循环,我认为这样做会得到更好的结果。
编辑:我更新了上面的代码,先收集所有根文件夹,然后创建空文件夹列表。然后你可以输出整个文件夹列表,过滤掉空的,它应该会给你一个包含文件的文件夹列表。试试上面的代码,看看它是否有效。当我在当地测试时,它对我有效。