我想下載使用線程匹配模式的多個文件。該模式可以匹配1或5或10個差異文件。java下載使用線程的多個文件
可以說爲了簡單起見,下載文件的實際代碼是在downloadFile()方法中,fileNames是與該模式匹配的文件名列表。我如何使用線程來做到這一點。每個線程只會下載一個文件。建議在for循環中創建一個新線程。
for (String name : fileNames){
downloadFile(name, toPath);
}
我想下載使用線程匹配模式的多個文件。該模式可以匹配1或5或10個差異文件。java下載使用線程的多個文件
可以說爲了簡單起見,下載文件的實際代碼是在downloadFile()方法中,fileNames是與該模式匹配的文件名列表。我如何使用線程來做到這一點。每個線程只會下載一個文件。建議在for循環中創建一個新線程。
for (String name : fileNames){
downloadFile(name, toPath);
}
你真的想用一個ExecutorService而不是單獨的線程,它是乾淨多了,有可能更高性能,將使你更輕鬆地後改變的事情上(線程數,線程名等):
ExecutorService pool = Executors.newFixedThreadPool(10);
for (String name : fileNames) {
pool.submit(new DownloadTask(name, toPath));
}
pool.shutdown();
pool.awaitTermination(Long.MAX_VALUE, TimeUnit.MILLISECONDS);
// all tasks have now finished (unless an exception is thrown above)
而且在你的類別處定義實際工作馬DownloadTask
:
private static class DownloadTask implements Runnable {
private String name;
private final String toPath;
public DownloadTask(String name, String toPath) {
this.name = name;
this.toPath = toPath;
}
@Override
public void run() {
// surround with try-catch if downloadFile() throws something
downloadFile(name, toPath);
}
}
的shutdown()
方法有一個非常混亂的名字,因爲它「將使以前提交的任務,以終止之前執行」。 awaitTermination()
聲明您需要處理的InterruptedException
。
是的,你可以創建內聯線程。
for (final String name : fileNames){
new Thread() {
public void run() {
downloadFile(name, toPath);
}
}.start();
}
是的,你當然可以在for循環中創建一個新的線程。事情是這樣的:
List<Thread> threads = new ArrayList<Thread>();
for (String name : fileNames) {
Thread t = new Thread() {
@Override public void run() { downloadFile(name, toPath); }
};
t.start();
threads.add(t);
}
for (Thread t : threads) {
t.join();
}
// Now all files are downloaded.
你也應該考慮使用Executor
,例如,由Executors.newFixedThreadPool(int)
創建一個線程池。
使用上面的代碼,我怎麼能限制同時下載的數量,說我只想一次下載3個文件。你有一個使用Executor – user373201
@ user373201的例子:按照我提供給'Executors.newFixedThreadPool(int)'的鏈接並查看@Phillip Reichart的答案。 – maerics
使用Executor,試試這個。
ExecutorService exec= Executors.newCachedThreadPool()
for (String name : fileNames){
exec.submit(new Runnable()
{
public void run()
{
downloadFile(name, toPath);
}
});
}
如果你想要說的三個下載同時運行,你可以使用:
Executors.newFixedThreadPool(3)
現在它阻塞while execute()'Runnable',你打算叫'exec.submit()':) –
@Philipp Reichart你真的知道你在說什麼嗎?執行時阻止什麼?聽着布魯夫!當你不知道你在說什麼時,避免標記人。 – Bitmap
是的,我確實曾經被這一次咬過。 ['Execute.execute()'](http://download.oracle.com/javase/1,5.0/docs/api/java/util/concurrent/Executor.html#execute(java.lang.Runnable))may 「...在Executor實現的判斷下,在新線程,共用線程或調用線程**中執行。「你真的想聲明變量爲'ExecutorService'並使用['submit()'](http://download.oracle.com/javase/6/docs/api/java/util/concurrent/ExecutorService.html#提交(java.lang.Runnable))。 –
所有上述提到的方法創建線程,但實際Concurreny沒有實現。
ExecutorService pool = Executors.newFixedThreadPool(5);
final File folder = new File("YOUR_FILES_PATH");
int l = folder.listFiles().length;
System.out.println("Total Files----"+folder.listFiles().length);
long timeStartFuture = Calendar.getInstance().getTimeInMillis();
pool.execute(new DownloadFile(folder,0,l/2));
pool.execute(new DownloadFile(folder,(l/2),l));
pool.shutdown();
try {
pool.awaitTermination(Long.MAX_VALUE, TimeUnit.MILLISECONDS);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
long timeEndFuture = Calendar.getInstance().getTimeInMillis();
long timeNeededFuture = timeEndFuture - timeStartFuture;
System.out.println("Parallel calculated in " + timeNeededFuture + " ms");
上述程序用於實現併發性,並請修改按您的要求。
這需要'downloadFile()'方法在'DownloadTask'(我的推薦)中定義,或者在外部聲明'static'。 –
'@Philipp Reichart'發佈'shutdown'後,新的下載任務將不會被游泳池接受。如果我是你,我會避免這種情況。 – Bitmap
這是一個沒有問題的問題,因爲在這種情況下關閉後沒有任何新任務添加到池中。第一個代碼片段應該存在於一個方法中,並在每次調用時創建一個新池。 –