2016-08-02 17 views
0

Ich entwickle ein einfaches Suchwerkzeug für meinen Zweck. Meine Absicht ist es, alle Dateien oder bestimmte Dateien im angegebenen Ordner zu durchsuchen. Ich dachte, mit mehreren Threads zu tun. Jeder Thread beginnt mit der Suche nach einer Datei und fügt diese Datei in eine Liste ein, wenn diese Datei nicht in der Liste enthalten ist. So wird jeder Thread nicht nach der gleichen Datei suchen.Suche nach einer Datei mit mehreren Threads

Ich bin mir nicht sicher, ob das der richtige Ansatz ist oder nicht. Und wenn ich das Programm ausführen, könnte ich das gleiche Ergebnis sehen, wenn ich einen Thread, zwei und sogar mehr als zwei verwenden.

Dann habe ich Executor Service, immer noch bekomme ich die gleiche Ausführungszeit.Ich konnte nicht den Unterschied finden. Meine Fragen sind unten.

1.Am ich benutze richtige Logik für die Suche Datei mit mehreren Threads?

2. kann ich den Unterschied bei der Ausführung mit einem Thread, zwei Threads, etc?

import java.io.File; 
import java.util.ArrayList; 
import java.util.List; 

public class FileReaderRunnable implements Runnable { 

    private List<File> fileList = new ArrayList<>(); 
    private File mfile; 

    public boolean finished; 
    public FileReaderRunnable(File file) { 
     this.mfile = file; 
    } 

    @Override 
    public void run() { 
     //System.out.println("Thread current:"+Thread.currentThread().getName()); 
     //while(!finished){ 
      getfiles(mfile); 
      //finished = false; 
     //} 

    } 

    public void setFlag(boolean value) { 
     finished = value; 
    } 

    public void getfiles(File file) { 
     System.out.println("EXecuting...: "+Thread.currentThread().getName()+file.getAbsolutePath()); 
     File[] listFiles = file.listFiles(); 
     if (listFiles != null && listFiles.length > 0) { 
      for (File file2 : listFiles) { 
       if(!fileList.contains(file2.getAbsoluteFile())){ 
        fileList.add(file2.getAbsoluteFile()); 
       }    
       getfiles(file2); 
      } 
     } 
    } 

    public List<File> getFiles(){ 
     return fileList ; 
    } 

} 

public class FileReaderThreadMain { 
    public static void main(String[] args) {   
     ExecutorService executor = Executors.newFixedThreadPool(30); 
     File file = new File("C:\\Temp"); 
     FileReaderRunnable r = new FileReaderRunnable(file); 
     long startTime = System.nanoTime(); 
     executor.execute(r);  
     executor.shutdown(); 
     // Wait until all threads are finish 
     while (!executor.isTerminated()) { 
     }  
     long endTime = System.nanoTime();  
     System.out.println("\nFinished all threads"); 
     System.out.println("main thread exited");  
     List<File> files = r.getFiles(); 
     System.out.println("Total Files size: "+files.size());  
     long duration = (endTime - startTime); 
     System.out.println("Duration: "+duration/1000000);  
    } 

} 
+2

Es scheint, dass es nur ein Thread ist, nicht wahr? –

+0

Sie haben nur eine Instanz von 'FileReaderRunnable', so dass es nur einen Worker gibt. Versuchen Sie, einige Instanzen davon zu erstellen, um "Executor" –

+0

zu liefern. Gibt es einen bestimmten Grund, warum Sie thread dafür verwenden? –

Antwort

0

Sie können es wie folgt tun:

public class Test { 

    private static final int THREAD_COUNT = 3; 
    private static int taskDoneCount=0; 
    public static void main(String[] args) throws Exception { 
     ExecutorService executor = Executors.newFixedThreadPool(THREAD_COUNT); 
     List<String> allFiles = new ArrayList<>(); 
     File dir = new File("C:\\Temp"); 
     File[] files = dir.listFiles(); 
     int length = files.length; 
     int onePart = length/THREAD_COUNT; 
     long startTime = System.currentTimeMillis(); 
     for (int i = 0; i < THREAD_COUNT; i++) { 
      int startIndex = i * onePart; // the start index of the file list 
      int endIndex = onePart * (i + 1);// the end index of the file list 
      if (i == THREAD_COUNT-1) { 
       endIndex = files.length; 
      } 
      System.out.println("Thread#"+(i+1)+" start index:"+startIndex+", end index:"+(endIndex-1)); 
      executor.execute(new SearchFileThread(startIndex, endIndex, files, fileList -> { 
       synchronized (Test.class) { 
        taskDoneCount++; 
        allFiles.addAll(fileList); 
        if (taskDoneCount == THREAD_COUNT) {// check if all tasks finished 
         executor.shutdown(); // shutdown the thread pool 
         System.out.println("allFiles = " + allFiles); 
         System.out.println("allFiles.size() = " + allFiles.size()); 
         System.out.println("Time used: "+(System.currentTimeMillis()-startTime)+"ms"); 
        } 
       } 
      })); 
     } 
    } 

    static private class SearchFileThread implements Runnable { 
     private int startIndex; 
     private int endIndex; 
     private File[] listFiles; 
     private List<String> fileList = new ArrayList<>(); 
     private TaskFinishListener listener; 

     public SearchFileThread(int startIndex, int endIndex, File[] listFiles, TaskFinishListener listener) { 
      this.startIndex = startIndex; 
      this.endIndex = endIndex; 
      this.listFiles = listFiles; 
      this.listener = listener; 
     } 

     public void run() { 
      for (int i = startIndex; i < endIndex; i++) { 
       fileList.add(listFiles[i].getAbsolutePath()); 
      } 
      listener.onFinish(fileList); 
     } 
    } 

    private interface TaskFinishListener { 
     void onFinish(List<String> fileList); 
    } 
} 
Verwandte Themen