Поскольку ваша программа является программой с графическим интерфейсом (я собираю ее по вызову repaint()
), она по своей сути многопоточная, даже если вы ее не знаете. (Если нет, он будет вести себя очень плохо.)
Если вы не используете потоки, то вы не можете использовать ожидание / уведомление или любой другой вид синхронизации, поскольку нет двух потоков для синхронизации. Но вам не обязательно явно использовать потоки в программе с графическим интерфейсом, чтобы в конечном итоге использовать потоки.
Обратите внимание, что компилятор Java не будет предупреждать вас, если вы используете методы, основанные на потоках, но на самом деле никоим образом не используете потоки.
У вас есть одна из следующих проблем:
1) Вы используете потоки, не зная об этом, и вы используете два разных объекта монитора. Таким образом, когда вы вызываете notify()
, он уведомляет монитор об этом объекте, но не о первом объекте, для которого вы вызываете wait()
. Есть много возможных решений. Одним из самых простых является использование для этого утилит параллелизма JDK 5, которые НАМНОГО лучше, чем встроенные базовые методы ожидания / уведомления монитора. Или,
2) Вы работаете в одном потоке, и ожидание / уведомление не годится. Просто в однопоточной программе не имеет смысла ждать, пока другой поток уведомит об этом, - нет другого потока, который может это сделать.
Предполагая, что вы на самом деле используете более одного потока, хороший способ решить эту проблему с помощью Java 5 и более поздних версий - использовать семафор , возможно, с помощью класса, содержащего mark()
, и немного упростить :
private final Semaphore sem = new Semaphore(1);
public void mark(int var) {
sem.acquire();
//change some stuff
repaint();
sem.release();
}
waitForSemaphore() {
sem.acquire();
}
, а затем в compute
, позвоните waitForSemaphore()
, когда хотите дождаться уведомления mark()
. Поскольку mark()
уже приобрел семафор, вам придется подождать, пока mark()
освободит семафор, прежде чем вычисления смогут получить его, вызвав waitForSemaphore()
.