参考以下代码。
for (Future<Long> future : list) {
try {
sum += future.get();
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}
现在,当我打电话给future.get时,这会阻止通话吗?因此,如果我在主线程和Android应用程序上执行此操作将导致ANR异常?我注意到也会抛出Interrupted异常,这是否意味着它们是在get函数中调用线程的睡眠?
答案 0 :(得分:5)
是的,Future.get()
的文档说:
如果需要等待计算完成,然后检索其结果。
因此,它会阻塞,直到计算结果可用,或计算被中断(取消或导致异常)。
如果您的计算需要很长时间才能完成,可能会导致ANR。
同样,来自Future.get()
的文档:
@throws InterruptedException如果当前线程在等待时被中断
现在,既然你从主线程调用了Future.get()
,我怀疑是Android系统会中断你的主线程,试图让它再次响应。但它也可能是由你的应用程序的另一个线程引起的 - 很难说,因为你没有指定你的应用程序做了什么,它创建了什么线程,何时,你使用ExecutorService(如果是这样,哪个实现),等等。
不,FutureTask.get()
(我认为是您正在使用的Future
的实现)不会调用Thread.sleep()
。相反,将线程置于等待模式是通过线程停放完成的,这使得在给出信号之前不会将其调度执行。如果在主线程中完成,这可能导致ANR错误。有关parking
机制的详细信息,请考虑阅读文档和this question
答案 1 :(得分:0)
您可以简单地检查未来是否已完成&#34;通过调用future.isDone()。代码示例:
String result = "";
if (myFuture.isDone()) result = (String) myFuture.get();
您可能希望在无限循环中检查它。
答案 2 :(得分:0)
提防#include <fstream>
#include <string>
#include <iostream>
#include <exception>
using namespace std;
void WriteToFile(ofstream* fileToWrite, std::string StringNeedsToWrite)
{
if (fileToWrite)
{
if (IsStartOfNewString(StringNeedsToWrite))
{
*fileToWrite << '\n';
}
*fileToWrite << StringNeedsToWrite;
}
else
{
throw exception();
}
}
的死锁。如果future.get()
,该调用MainThread
和future.get()
都被同步(在同一对象上),则会出现死锁。