我有一些数据处理,我正在一个名为“myServlet”的servlet中执行(例如),有时我收到大量数据要同时处理,我的意思是同时exaclty,我需要一种方法告诉客户端服务器正忙。
我尝试在应用程序启动时将ServletContext中的属性初始化为false,然后当我收到请求时,我检查属性是否为false,如果是这种情况我将其更改为true然后我处理,这样只要我正在处理,下一个请求就会被删除。当我同时收到几个请求,服务器同时处理所有请求时,这不能正常工作,我认为有些请求甚至在我将ctx属性更改为TRUE之前就已转义....我认为我'我错过了什么
这就是我想知道是否有办法检查是否已经有数据处理,以便我在那时停止并将服务器忙响应发送给客户端
希望你们有这个想法(问题)
提前感谢...
答案 0 :(得分:1)
你可以使用ReentrantLock
(在上下文中代替boolean,在上下文或某个地方保持这个锁 - 它应该是对这个servlet的所有请求中的相同实例),你还需要将锁定操作同步到确保你在服务器已经忙碌的时候回到忙碌的任何人,请阅读api和这个课程的例子,基本的想法是:
public class SomeService {
private final ReentrantLock lock = new ReentrantLock(); // or store it in context based on your needs
// ...
/** this method refuse to process if there is already ongoing processing */
public void heavyProcessing() {
synchronized (lock) {
if (lock.isLocked()) {
// return busy status here
return;
}
lock.lock(); // acquire the lock - here we have the winner request that will be processed
}
try {
// ... do the processing here
} finally {
lock.unlock()
}
}
}
这完全是因为" Out of Order Execution"。 ReentrantLock是线程安全的,但Boolean
或boolean
不是。您还需要同步(synchronized
块)以确保在正在进行的处理过程中告知正确的状态。
因为:
如果没有在Threads之间进行适当的同步,则无法保证porgram按照其编写的确切顺序执行(如果不影响单线程程序,优化机制可以改变执行顺序)。要防止此类OOE优化,您需要指定一些同步点。 ReenterantLock
的设计考虑到了这一点,boolean
不是。 ReenterantLock
的使用只是将这些同步点放入已执行的代码中,因此您可以获得正确的同步。
java中线程之间的同步是非常广泛的主题,我不能在这里教你如何做到这一点。关于这个主题的好书之一是#34; Java Concurrency in Practice"。我建议先阅读这本书,然后在这里询问是否会让你感到困惑。