2011-08-25 21 views
5

一部の内部ファイルを除くフォルダをコピーJavaは、私がこのような構造でフォルダを持っている

mainFolder

--Sub1 
     --File .scl 
     --File .awl 
     --Other files 
    --Sub2 
     --Files 
    --Sub3 
    --Sub4 

私は別の場所にコピーしたいが、私はSUB3を回避して(から依存することにしたいです状況が)ここでSub1を

からいくつかのファイルは、私がこれまでやったからの抜粋です:

FileUtils.copyDirectory(srcDir, dstDir, new FileFilter() { 
     public boolean accept(File pathname) { 
      // We don't want 'Sub3' folder to be imported 
      // + look at the settings to decide if some format needs to be 
      // excluded 
      String[] ignoreList= new String[]{ 
        !Settings.getSiemensOptionAWL() ? ".awl":"uselessStringWilNeverBeFound", 
        !Settings.getSiemensOptionSCL() ? ".scl":"uselessStringWilNeverBeFound", 
        "Sub3" 
      }; 

      return !(ignoreFile(pathname, ignoreList) && pathname 
        .isDirectory()); 
     } 
    }, true); 


    public static boolean ignoreFile(File file, String[] ignoreList) { 
     for (final String ignoreStr : ignoreList) 
      if (file.getAbsolutePath().contains(ignoreStr)) 
       return true; 
     return false; 
    } 

それは明らかに縫い目があります。しかし、私は非常に醜い解決策だと思う.... 誰も良い方法を知っていますか?

P.S:コースSettings.getSiemensOptionAWLの は()だけブール関数である私の決定を返すtaht

+2

ディレクトリ全体を新しい場所にコピーしてから削除するのは簡単でしょうそこにあるべきではないファイル(そのコピーから)。明らかに、原動力が基本機能ではなくセキュリティに関連している場合、これは適切ではありません。 –

+0

私はあなたが何を意味するのか見ています...しかし、あなたが何を持っていないデータをコピーする危険性があるのか​​はわかりません。(thiはそうではありませんが、私は清潔な解決策を持っています):) – Stefano

+0

でも...明らかにときどき動作しますが、いつかはそうではありません...おそらく同じ考え方には良い方法があります! – Stefano

答えて

4

他のオプションが良いです、しかし別の代替は、(もちろん、やり過ぎかもしれない!)一緒に巣複数の単純FileFiltersにあるその後

public class FailFastFileFilter implements FileFilter { 
    protected final List<FileFilter> children = new ArrayList<FileFilter>(); 

    public FailFastFileFilter(FileFilter... filters) { 
     for (FileFilter filter: filters) { 
      if (filter != null) 
       this.filters.add(filter); 
     }  
    } 

    public boolean accept(File pathname) { 
     for (FileFilter filter: this.filters) { 
      if (!filter.accept(pathname)) { 
       return false; // fail on the first reject 
      } 
     } 

     return true; 
    } 
} 

Sub3の場合は簡潔で簡潔なFileFiltersを、.sclと.awlの場合は単純に組み合わせてください。上記のFailFastFileFilterの例では、フィルタの1つとしてnullを指定できます(インラインif文を使用して特定のFileFilterを適用するかどうかを判断できます)。 Sub1のケースとSub3のケースの子フィルタを実装します。

まず、ディレクトリ内の特定の拡張子を持つファイルを除外するフィルタ:

public class ExcludeExtensionInDirFileFilter implements FileFilter { 
    protected final String parentFolder; 
    protected final String extension; 

    public ExtensionFileFilter(String parentFolder, String extension) { 
     this.parentFolder = parentFolder; 
     this.extension = extension.toLowerCase(); 
    } 

    public boolean accept(File file) { 
     if (!file.isDirectory() && file.getParentFile().getName().equalsIgnoreCase(parentFolder)) 
      return !file.getAbsolutePath().toLowerCase().endsWith(extension); 
     else 
      return true; 
    } 
} 

次にディレクトリを除外するために:

:FailFastFileFilterの設定

public class ExcludeDirFileFilter implements FileFilter { 
    protected final String name; 

    public ExcludeDirFileFilter(String name) { 
     this.name = name.toLowerCase(); 
    } 

    public boolean accept(File file) { 
     if (file.isDirectory() && file.getName().equalsIgnoreCase(name)) 
      return false; 
     else 
      return true; 
    } 
} 

が、その後のようになります。

FileFilter filters = new FailFastFileFilter(
    new ExcludeDirFileFilter("Sub3"), // always exclude Sub3 
    (!Settings.getSiemensOptionAWL() ? new ExcludeExtensionInDirFileFilter("Sub1",".awl"), null), // Exclude Sub1/*.awl if desired 
    (!Settings.getSiemensOptionSCL() ? new ExcludeExtensionInDirFileFilter("Sub1",".scl"), null) // Exclude Sub1/*.scl if desired 
); 

FileUtils.copyDirectory(srcDir, dstDir, filters); 
-1

は、私にはかなりきれいに見えます。すべてのコードを直接呼び出しコードに入れないでください。そうすることで、いつも見ている必要はありません。このコードをすべて隠す独自のCopySubDirクラスを作成し、そのコードを簡単に理解できるようにします。その後、呼び出しコードはきれいに見えます。

1

石で固定された弦の場合ですか?たぶん

new FileFilter() { 
    public boolean accept(File pathname) { 
     String path = pathname.getAbsolutePath().toLowerCase(); 

     return (!pathname.isDirectory() || path.endsWith("sub3")) && 
      (!Settings.getSiemensOptionAWL() && path.endsWith(".awl")) && 
      (!Settings.getSiemensOptionSCL() && path.endsWith(".scl")); 
    } 
} 
+0

これはもっと良く見えるが、文字列は固定されていない。...ソフトウェアの設定に依存する... – Stefano

+0

コード/説明。多分あなたは可変パターンのデコレータ/連鎖パターンを使用して、より小さなconfigファイルフィルタを構成することになります。 – vickirk

+0

ピーターの答えのラインに沿って何か! – vickirk

3

のようなもの、私は醜さは必ずしも有用な情報の一部は(実際には文字列はファイル拡張子などである、重要でどの文字列)また、その配列があることを行っている失いignoreFile()を、導入から来ていると思います階層内のすべてのファイルに対して作成されますが、これは非常に非効率的です。代わりに、このような何かを考えてみましょう。ここで提案

FileUtils.copyDirectory(srcDir, dstDir, new FileFilter() { 
    public boolean accept(File pathname) { 
     // We don't want 'Sub3' folder to be imported 
     // + look at the settings to decide if some format needs to be 
     // excluded 
     String name = pathname.getName(); 
     if (!Settings.getSiemensOptionAWL() && name.endsWith(".awl")) 
      return false; 
     if (!Settings.getSiemensOptionSCL() && name.endsWith(".scl")) 
      return false; 

     return !(name.equals("Sub3") && pathname.isDirectory()); 
    } 
}, true); 
+0

これはきれいな解決策ですが、復帰後の最初の用語は!pathName.equals( "Sub3")の代わりに!name.equals( "Sub3")だったはずです。 –

+0

これを修正し、 "isDirectory()"の部分を明らかにしました... –

関連する問題