代码之家  ›  专栏  ›  技术社区  ›  LA_MAR2

我想从递归搜索和复制中排除子文件夹

  •  0
  • LA_MAR2  · 技术社区  · 4 年前

    我想在目录“x”中递归查找文件类型“y”,不包括子目录“m”,并将文件复制到子目录“m”

    我正在尝试这个

    $TargetDir = read-host "Please enter target Dir"
    $sourceDir = read-host "Please enter source Dir" 
    $format = read-host "Format to look for" 
    Get-ChildItem -Path $sourceDir -Recurse -Filter $format | where  FullName -Not -Like $TargetDir | 
    Copy-Item -Destination $TargetDir
    
    1 回复  |  直到 4 年前
        1
  •  1
  •   Alex R.    4 年前

    你最好试试用 foreach 循环。以下是搜索照片和视频的示例。

    # Making an array of all files from Get-ChildItem
    $searchItems = Get-ChildItem -Path $sourceDir -Recurse -Include *.mp4,*.jpg,*.jpeg | where  FullName -notlike $TargetDir
    # Copy files one by one in cycle
    foreach($currentFile in $searchItems) {
      Copy-Item -Path $currentFile.Fullname -Destination $TargetDir
    }
    
        2
  •  0
  •   LA_MAR2    4 年前

    我想明白了,但最好能解释一下 代码:

       $TargetDir = read-host "Please enter target Dir"
       $sourceDir = read-host "Please enter source Dir"
       $format = read-host "Format to look for"
       $folders = Get-ChildItem -Path $sourceDir -Recurse -filter $format | Where 
       {($_.PSIsContainer) -and ($TargetDir -notcontains $_.Name)}
       foreach ($f in $folders){
       Write-Host "These Files will be copied: $f"
       Copy-Item - path $sourceDir$f -Destination $TargetDir\$f -Recure -Force}
    

    我不明白:

      Where {($_.PSIsContainer) -and ($TargetDir -notcontains $_.Name)}
    

    为什么

    Write-Host "These Files will be copied: $f"
    

    运行时未显示

        3
  •  0
  •   postanote    4 年前

    这个。。。

    [写入主机“这些文件将被复制:$f”]

    …是因为你正在做的是一个循环,写主机清除缓冲区。除了需要彩色屏幕输出时,写主机大多没用。好吧,除了一些格式化用例。一般来说,不要使用它。就连PowerShell的作者也这么说。

    除非另有说明,否则屏幕的输出是PowerShell默认值。写主机的更好选择是写输出,或输出主机或T形对象。请参阅有关其详细信息的帮助文件。

    Get-ChildItem有几个开关,如果你只想要目录,有一个开关可以用来切换,还有一个开关是-Exclude,你知道的。

    # Get specifics for a module, cmdlet, or function
    (Get-Command -Name Get-ChildItem).Parameters
    (Get-Command -Name Get-ChildItem).Parameters.Keys
    # Results
    <#
    ...
    Exclude
    ...
    Directory --- (This is what that $_.PSIsContainer/$PSItem.PSIsContainer this is doing, but that is legacy stuff.)
    ...
    #>
    Get-help -Name Get-ChildItem -Examples
    Get-help -Name Get-ChildItem -Full
    Get-help -Name Get-ChildItem -Online
    

    About Objects --- Objects in Pipelines

    因此。。。

    # Get directory names only and return only the full UNC
    (Get-ChildItem -Directory -Path 'D:\SourceFolder'-Recurse).FullName
    # Results
    <#
    D:\SourceFolder\est
    D:\SourceFolder\here
    D:\SourceFolder\hold
    D:\SourceFolder\TargetFolder
    #>
    
    # Just like the above, but exclude the TargetFolder
    (Get-ChildItem -Directory -Path 'D:\SourceFolder' -Exclude 'TargetFolder' -Recurse).FullName
    # Results
    <#
    D:\SourceFolder\est
    D:\SourceFolder\here
    D:\SourceFolder\hold
    #>
    

    所以,对你的代码进行一个小的重构。

    # Recursively get all text files, in all directories, except one for copy action
    Get-ChildItem -Path 'D:\SourceFolder' -Filter '*.txt' -Exclude 'TargetFolder' -Recurse |
    ForEach { 
        "These Files will be copied: $($PSItem.FullName)"
    
        # Remove the -whatIf for the actual run.
        Copy-Item -Path $PSItem.FullName -Destination 'D:\SourceFolder\TargetFolder' -Recurse -WhatIf 
    }
    # Results
    <#
    These Files will be copied: D:\SourceFolder\here\mytest - Copy.txt
    What if: Performing the operation "Copy File" on target "Item: D:\SourceFolder\here\mytest - Copy.txt Destination: D:\SourceFolder\TargetFolder\mytest - Copy.txt".
    These Files will be copied: D:\SourceFolder\here\mytest.txt
    What if: Performing the operation "Copy File" on target "Item: D:\SourceFolder\here\mytest.txt Destination: D:\SourceFolder\TargetFolder\mytest.txt".
    These Files will be copied: D:\SourceFolder\hold\awél.txt
    What if: Performing the operation "Copy File" on target "Item: D:\SourceFolder\hold\awél.txt Destination: D:\SourceFolder\TargetFolder\awél.txt".
    #>
    

    当然,你需要调整上述变量,并删除所有注释。评论是一件好事,但过度评论和评论不足或糟糕/难以理解的评论一样糟糕。所有这些都有自己的偏好。

    我的规则:

    1. 不要对显而易见的事情发表评论,因为代码本身就说明了一切。
    2. 不要使用只有你知道或记得的速记。
    3. 用简单明了的本地化语言写作。
    4. 为那些不了解你或速记的人写作,他们会跟随你或可能使用/审查你的代码;他们可以而且经常是新手。