標籤:
FilenameFilter & FileFilter
FilenameFilter 和 FileFilter 都是用來過濾檔案,例如過濾,以.jpg或者.java結尾的檔案,通過看他們的源碼:通過使用File類中String[] list(FilenameFilter filter)或者public File[] listFiles(FileFilter filter)方法,把FilenameFilter或者FileFilter介面對象作為參數傳入,通過實現介面裡面的 boolean accept(File dir, String name) 或者boolean accept(File pathname)方法來過濾出滿足條件的檔案。區別:FilenameFilter的效能比FileFilter的好.
public File[] listFiles(FileFilter filter)
返回抽象路徑名數組,這些路徑名表示此抽象路徑名表示的目錄中滿足指定過濾器的檔案和目錄。除了返回數組中的路徑名必須滿足過濾器外,此方法的行為與 listFiles() 方法相同。如果給定 filter 為 null,則接受所有路徑名。否則,若且唯若在路徑名上調用過濾器的 FileFilter.accept(java.io.File) 方法返回 true 時,該路徑名才滿足過濾器。
/**
File類:
* 使用 String[] list(FilenameFilter filter)遍曆指定目錄下面,指定的尾碼的檔案。
底層怎麼實現過濾的?
String[] list(FilenameFilter filter)
原理:先把目錄下面的檔案調用list()方法全部存放到一個String[]數組裡面,然後遍曆數組,
把符合filter.accept(this, names[i])條件的放到一個ArrayList裡面,然後把
List轉化為String[]數組
底層源碼解析:
public String[] list(FilenameFilter filter) {
String names[] = list();//把所有目錄檔案列出來
if ((names == null) || (filter == null)) {//如果沒有目錄或者檔案,返回null
return names;
}
ArrayList v = new ArrayList();
for (int i = 0 ; i < names.length ; i++) {//找到檔案,遍曆
if (filter.accept(this, names[i])) {
v.add(names[i]);/把滿足條件的放到List集合中
}
}
return (String[])(v.toArray(new String[v.size()]));
}
* FilenameFilter 介面
* 介面方法:
* boolean accept(File dir,String name) 可以使用此方法列出指定目錄下面的帶有某些尾碼的檔案。
參數:
dir - 被找到的檔案所在的目錄。
name - 檔案的名稱。
返回:
若且唯若該名稱應該包含在檔案清單中時返回 true;否則返回 false。
*
*/
代碼:
1.需求找出某個路徑下面以.java結尾的檔案。
實現:FilenameFilter 介面:
package com.lp.ecjtu.File.filter;import java.io.File;import java.io.FilenameFilter;public class FileterByJava implements FilenameFilter { private String SufixName;//傳入過濾的名稱 public FileterByJava(String SufixName){ this.SufixName = SufixName; } @Override public boolean accept(File dir, String name) { //System.out.println("dir"+dir+"_____"+"name"+name);//返回dir:E:\workspace\IOTest_____name:buf.txt }}
package com.lp.ecjtu.File.filter;import java.io.File;import java.io.FilenameFilter;public class FileListFilter { public static void main(String[] args){ ListFileFileterByjava(); } /** * * 使用實現FilenameFilter介面的方法, * 過濾String[] list(FilenameFilter filter) * 檔案名稱過濾 */ public static void ListFileFileterByjava(){ File f = new File("E:"+File.separator+"workspace"+File.separator+"IOTest"); String[] fileNames = f.list(new FileterByJava(".java"));//使用具體對象,把過濾後的以.java檔案的檔案放到數組當中 System.out.println(fileNames.length);//含有.java檔案數組的長度 for(String name:fileNames){//遍曆找到的.java檔案 System.out.println(name); } } /** * 列出指定目錄下,尾碼為.java的檔案,使用方法String[] list(FilenameFilter filter)使用匿名內部類的方法 */ public static void ListFileNameFileter(){ File f = new File("E:"+File.separator+"workspace"+File.separator+"IOTest"); String[] files = f.list(new FilenameFilter() {//使用匿名內部類的方法 @Override public boolean accept(File dir, String name) { // TODO Auto-generated method stub //System.out.println("dir:"+dir+"name....."+name);//測試說明dir表示指定目錄,name表示指定目錄的名稱 return name.endsWith(".java");//通過匿名內部類的傳回值來控制指定目錄下面的檔案和檔案夾的顯示,只顯示.java檔案 } }); System.out.println(files.length); //遍曆指定目錄下面的檔案和目錄 for(String file:files){ System.out.println(file); } }}
/ * FileFilter介面
* 介面方法:
* boolean accept(File dir) 可以使用此方法列出指定目錄下面的帶有某些尾碼的檔案。
參數:
dir - 被找到的檔案所在的目錄。
返回:
若且唯若該名稱應該包含在檔案清單中時返回 true;否則返回 false。
*/
代碼:
需求:現在要求輸入一個檔案的目錄,之後將裡面所有的備份檔案刪除,備份檔案都是以“.bak”或".BAK"結尾,也就是說過濾檔案類型為.bak或者.BAK檔案後進行刪除.
第一種方法,使用FileFilter內部類的方法,進行操作:
代碼:
package com.lp.ecjtu.File.filter;import java.io.File;import java.io.FileFilter;public class FileFilterDemo { public static void main(String[] args){ File dir = new File("E:\\複件 demodir"); ListFileFileter(dir); } /** * 現在要求輸入一個檔案的目錄,之後將裡面所有的備份檔案刪除,備份檔案都是以“.bak”或".BAK"結尾,過濾檔案類型為.bak檔案 */ public static void ListFileFileter(File dir){ if(dir.exists()){ //匿名內部類,把FileFilter介面對象作為參數 File[] files = dir.listFiles(new FileFilter() { @Override public boolean accept(File pathname) { if(pathname.isDirectory()){ return true; } String name = pathname.getName();//擷取檔案的名稱E:\複件 demodir\Learn\sgim_piccell.v1.bin.bak System.out.println("****************"+pathname); return name.endsWith(".bak")|| name.endsWith(".BAK");//過濾檔案類型為.bak或者.BAK檔案,而不包含.BAK或者.bak的檔案 } }); //深度遍曆檔案,遞迴 for(int i=0;i<files.length;i++){ if(files[i].isFile()){//如果遍曆到的是檔案,直接刪除 files[i].delete(); }else{//還是目錄,繼續遍曆,直到是檔案,再刪除 ListFileFileter(files[i]); } } }else{ throw new RuntimeException("操作的檔案或者目錄不存在!"); } }}
第二中方法實現介面,使用真實類的對象:
package com.lp.ecjtu.File.filter;import java.io.File;import java.io.FileFilter;import java.io.FilenameFilter;/** * * 需求:輸入一個檔案目錄,之後將裡面所有備份的檔案刪除,備份檔案都是以".bak" 和".BAK"結尾 * */public class FileterByFile implements FileFilter { @Override public boolean accept(File pathname) { if(pathname.isDirectory()){ return true; } String name = pathname.getName(); // TODO Auto-generated method stub System.out.println("****************"+pathname); return name.endsWith(".bak")|| name.endsWith(".BAK"); } }
package com.lp.ecjtu.File.filter;import java.io.File;import java.io.FileFilter;public class FileFilterDemo { public static void main(String[] args){ File dir = new File("E:\\複件 demodir"); ListFileFileterBak(dir); } /**
* 刪除滿足條件的檔案
* @param dir
*/ public static void ListFileFileterBak(File dir){ if(dir.exists()){ File[] files = dir.listFiles(new FileterByFile());//使用過濾 for(File file:files){ if(file.isDirectory()){ ListFileFileterBak(file); }else{ file.delete(); } } }else{ throw new RuntimeException("操作的檔案或者目錄不存在!"); } }}
【轉】File類應用 - FilenameFilter 和 FileFilter