我可以问一个新手Java问题吗?
我正在从网上下载一些文件。此方法下载(url location)被多次调用。
public static void download(final String url) {
Thread t = new Thread("download") {
@Override
public void run() {
try {
synchronized (object) {
// download & save
}
} catch(Exception e) {}
}
};
t.start();
}
我添加了“synchronized”,以便逐个下载。 (不是同时发生多次下载) 我猜即使send()被多次调用,synchronized会阻塞其他线程,直到第一个线程完成。
以上代码是否有效?还是我必须实施队列?然后一个一个地出列? 可以同步阻止“足够”的线程吗? (30?50?)或是否有限制?
答案 0 :(得分:3)
以上代码是否有效?
是的,只要object
引用所有线程中的同一个对象,synchronized块中的代码一次只能由一个线程执行。
[...]或者我必须实施队列?然后一个一个地出列?
一般来说,我建议您尽可能使用高级构造(例如来自java.util.concurrent包)。例如,您可以考虑对这些类型的事物使用执行程序服务。
[...]可以同步阻止“足够”的线程吗? (30?50?)或是否有限制?
不,没有限制。至少不接近30或50: - )
答案 1 :(得分:3)
以下是如何操作:
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class QueueDownloader {
private final ExecutorService executor = Executors.newSingleThreadExecutor();
public void download(final String url) {
executor.execute(new Runnable() {
@Override
public void run() {
// download & save
}
});
}
}
这将在单个后台线程上排队所有可运行的(即下载)。
答案 2 :(得分:0)
如果可以避免创建其他线程,通常应该这样做。据我所知,你从不想要并行使用两个工作项(下载),所以最好的想法是性能方面是使用由单个工作线程轮询的并发队列实现。