在Java中等待的最佳方式(Best way to wait in Java)

我有一个应用需要等待一段未知的时间。 它必须等到服务器填充了几个数据字段。

服务器的API为我提供了一种请求数据的方式,非常简单...

服务器的API还提供了一种方法来一次接收我的数据,一次一个字段。 它没有告诉我什么时候所有的字段都完成了填充。

在我的请求完成服务器处理之前,最有效的方法是什么? 这是一些伪代码:

public class ServerRequestMethods { public void requestData(); } public interface ServerDeliveryMethods { public void receiveData(String field, int value); } public class MyApp extends ServerRequestMethods implements ServerDeliveryMethods { //store data fields and their respective values public Hashtable<String, Integer> myData; //implement required ServerDeliveryMethods public void receiveData(String field, int value) { myData.put(field, value); } public static void main(String[] args) { this.requestData(); // Now I have to wait for all of the fields to be populated, // so that I can decide what to do next. decideWhatToDoNext(); doIt(); } }

我必须等到服务器完成我的数据字段的填充后,服务器才会在请求完成时通知我。 所以我必须继续检查我的请求是否已完成处理。 什么是最有效的方法来做到这一点?

wait()和notify(),用一个守护while循环的方法来检查每次我被notify()唤醒时是否还有所有必需的值?

Observer和Observable,并且每次调用Observer.Update()时都会检查是否具有所有必需的值?

什么是最好的方法? 谢谢。

I have an app that needs to wait for some unknown amount of time. It must wait until several data fields are finished being populated by a server.

The server's API provides me a way to request data, easy enough...

The server's API also provides a way to receive my data back, one field at a time. It does not tell me when all of the fields are finished being populated.

What is the most efficient way to wait until my request is finished being processed by the server? Here's some pseudocode:

public class ServerRequestMethods { public void requestData(); } public interface ServerDeliveryMethods { public void receiveData(String field, int value); } public class MyApp extends ServerRequestMethods implements ServerDeliveryMethods { //store data fields and their respective values public Hashtable<String, Integer> myData; //implement required ServerDeliveryMethods public void receiveData(String field, int value) { myData.put(field, value); } public static void main(String[] args) { this.requestData(); // Now I have to wait for all of the fields to be populated, // so that I can decide what to do next. decideWhatToDoNext(); doIt(); } }

I have to wait until the server is finished populating my data fields, and the server doesn't let me know when the request is complete. So I must keep checking whether or not my request has finished processing. What is the most efficient way to do this?

wait() and notify(), with a method guarding the while loop that checks if I have all of the required values yet every time I'm woken up by notify()?

Observer and Observable, with a method that checks if I have the all the required values yet every time my Observer.Update() is called?

What's the best approach? Thanks.

最满意答案

如果我理解你的话,其他一些线程在你的MyApp上调用receiveData来填充数据。 如果这是正确的,那么你就是这么做的:

你这样睡觉:

do { this.wait(someSmallTime); //We are aquiring a monitor on "this" object, so it would require a notification. You should put some time (like 100msec maybe) to prevent very rare but still possible deadlock, when notification came before this.wait was called. } while (!allFieldsAreFilled());

receiveData应该发出notify呼叫,以unpause您的wait呼叫。 例如像这样:

myData.put(field, value); this.notify();

这两个块都需要在this对象上“同步”才能获得它的监视器(这是wait所需的)。 您需要将方法声明为“同步”,或者将各个块放入synchronized(this) {...}块中。

If I understood you right, some other thread calls receiveData on your MyApp to fill the data. If that's right, then here's how you do it:

You sleep like this:

do { this.wait(someSmallTime); //We are aquiring a monitor on "this" object, so it would require a notification. You should put some time (like 100msec maybe) to prevent very rare but still possible deadlock, when notification came before this.wait was called. } while (!allFieldsAreFilled());

receiveData should make a notify call, to unpause that wait call of yours. For example like this:

myData.put(field, value); this.notify();

Both blocks will need to be "synchronized" on this object to be able to aquire it's monitor (that's needed for wait). You need to either declare the methods as "synchronized", or put the respective blocks inside synchronized(this) {...} block.

更多推荐