.net Powershell - IO.Directory - 在所有子目录中查找文件类型

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/14970692/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-03 16:53:22  来源:igfitidea点击:

Powershell - IO.Directory - Find file types in all subdirectories

.netpowershell

提问by user2089287

I ran across this code in another post that almost does what I need, but can't figure out how to modify it to look for specific file types, i.e. *.bak, .txt, etc. I'm using Powershell with [System.IO.DirectoryInfo] because, like others have stated, using Get-ChildItem is too slow across the network. I thought it would just be something like $fileEntries = [IO.Directory]::GetFiles("C:\", ".bak"), but it still returns every file in every directory. --PS/.NET newbie

我在另一篇几乎满足我需要的帖子中遇到了这段代码,但无法弄清楚如何修改它以查找特定的文件类型,即 *.bak、.txt 等。我正在使用 Powershell 和 [System .IO.DirectoryInfo] 因为,正如其他人所说,使用 Get-ChildItem 在网络上速度太慢。我以为它只是类似于 $fileEntries = [IO.Directory]::GetFiles("C:\", ".bak"),但它仍然返回每个目录中的每个文件。--PS/.NET 新手

try
{
       $fileEntries = [IO.Directory]::GetFiles("C:\")
       [System.IO.DirectoryInfo]$directInf = New-Object IO.DirectoryInfo("C:\")
       $folders = $directInf.GetDirectories()
}
catch [Exception]
{
       $_.Exception.Message
       $folders = @()
 }

foreach($fileName in $fileEntries) 
{

      #[Console]::WriteLine($fileName); 

}

Remove-Variable -ErrorAction SilentlyContinue -Name fileEntries 

foreach($folder in $folders)
{
    recurse("C:\" + $folder + "\")
}

回答by Musaab Al-Okaidi

This will loop through each extension searching for all files in the root and sub-directories. Ensure you have the correct privileges on all the directories especially when you're running from C:\ as the root.

这将遍历每个扩展名,搜索根目录和子目录中的所有文件。确保您对所有目录具有正确的权限,尤其是当您以根目录从 C:\ 运行时。

$Extensions = @(".bak",".csv",".txt")

Foreach ( $Extension in $Extensions )
{
   [System.IO.Directory]::EnumerateFiles("C:\","*$Extension","AllDirectories")
}

This method will only work with Powershell running .Net 4.0 or higher. To check and update the version of .Net:

此方法仅适用于运行 .Net 4.0 或更高版本的 Powershell。要检查和更新 .Net 的版本:

$PSVersionTable

Name                           Value
----                           -----
CLRVersion                     2.0.50727.4971
BuildVersion                   6.1.7600.16385
PSVersion                      2.0
WSManStackVersion              2.0
PSCompatibleVersions           {1.0, 2.0}
SerializationVersion           1.1.0.1
PSRemotingProtocolVersion      2.1

The CLRVersion value is the .net version.

CLRVersion 值是 .net 版本。

Update the config file as follows:

更新配置文件如下:

$Config = @"
<?xml version="1.0"?>
<configuration>
    <startup useLegacyV2RuntimeActivationPolicy="true">
        <supportedRuntime version="v4.0.30319"/>
        <supportedRuntime version="v2.0.50727"/>
    </startup>
</configuration>
"@

$Config > $PSHOME\Powershell.exe.config

Restart the Powershell session and verify the CLRVersion value in the $PSVersionTable variable.

重新启动 Powershell 会话并验证 $PSVersionTable 变量中的 CLRVersion 值。

回答by user2089287

This worked after creating a config file to use the .NET 4.0 Framework:

这在创建配置文件以使用 .NET 4.0 Framework 后起作用:

try{
    $path = "\$Server$($drive.replace(':','$'))"
    foreach ($filepath in [System.IO.Directory]::EnumerateFiles($path,"*.bak","AllDirectories"))
       {
          $file = New-Object System.IO.FileInfo($filepath)
          write-host $file
          # insert file into database table
       }
  }
catch [UnauthorizedAccessException]
  {
     $exception = $_.Exception.Message #I don't need to write/insert exception
  }

回答by Manny

Here's a simple PowerShell script to move many files from a directory into a structured directory by year, month and day. This is very fast, I had over 500K files.

这是一个简单的 PowerShell 脚本,用于按年、月和日将许多文件从目录移动到结构化目录中。这非常快,我有超过 50 万个文件。

$listofFiles =   [System.IO.Directory]::EnumerateFiles("D:\LotsOfFiles","*.*","TopDirectoryOnly")

$listofFiles |% {
   $file = New-Object System.IO.FileInfo($_)    
   $date = Get-Date ($file.CreationTime)
   $filepath = ("{0}\{1:00}\{2:00}-{3}\{4:00}\" -f "D:\LotsOfFiles", $date.year, 
   $date.month, $date.toString("MMM"), $date.day)
   Write-Output ("Move: {0} to {1}" -f $file.Fullname, $filepath)

   if (! (Test-Path $filepath)) {       
      new-item -type Directory -path $filepath      
   }

   move-item $file $filepath
}   

This probably can be improved but it works.

这可能可以改进,但它有效。