Но я не уверен, куда я должен поставить попытку и поймать, я могу окружить весь синхронизированный блок или только lock.wait ()? Что такое эмпирическое правило и действительно ли это важно?
lock.wait()
is the only line that can throw an exception in your block
method. So whether you put your try/catch around the wait or include the whole method body does not make a difference from an execution perspective (assuming you exit the loop in both cases of course - if you want to continue looping then the try/catch block should obviously be within the loop).
Другими словами, это только вопрос стиля - см. этот другой обсуждение . Я лично считаю, что это более читаемо:
try {
synchronized (lock) {
while (!loaded) {
lock.wait();//Unhandled exception type InterruptedException
}
}
} catch (InterruptedException e) {
//to ignore me or not to ignore me, that is the question
Thread.currentThread().interrupt();
}
Для обработки можно нормально вызвать Thread.currentThread (). interrupt() в этой ситуации?
В первом примере ниже можно поймать InterruptedException и выйти из цикла без повторного прерывания потока, поскольку в любом случае метод run будет завершен, и поток будет умирать:
new Thread(new Runnable() {
@Override
public void run() {
block();
}
}).start();
Во втором примере, приведенном ниже, вы, безусловно, должны повторно прервать поток, чтобы позволить методу запуска узнать, была ли причина, из-за которой завершился block()
, что загруженный стал истинным или что он был прерван:
public void run() {
while(!Thread.currentThread().isInterrupted()) {
loaded = false;
System.out.println("Launching data load");
block(); //if false has become true, loop, if interrupted, exit
}
}
Если вы не знаете, как будет использоваться метод, хорошие манеры предполагают, что вы должны повторно прервать поток.