(Servlet,线程安全)保护会话和上下文状态



参考:Head First Servlet&JSP,第204页,第三个问题:

Q。"实现SingleThreadModel的效果实际上是与同步服务方法相同。二者都可以在没有保护的情况下让网络应用程序屈服会话和上下文状态。"

这意味着什么:"在不保护会话和上下文状态的情况下让网络应用屈服"?他们是说实现SingleThreadModel还不够线程安全吗?因为即使一个servlet一次只能运行一个线程,这也不会阻止其他servlet访问和更改上下文/会话范围的变量?如果Servlet实现了SingleThreadingModel,那么为什么需要保护会话状态呢?它一次只允许一个线程。我认为,即使您打开一个新的浏览器窗口,servlet也不允许您发出两个请求。也许他们的意思是,如果不同步上下文/会话状态,一次只有一个线程的不同Servlet仍然可能破坏该状态?

为什么类(静态)变量不是线程安全的?因为所有线程都可以访问和修改(损坏)该值?

这对我来说还是有点模糊。

参考:Head First Servlets&JSP,第204页,第三个问题:

Q。"实现SingleThreadModel的效果实际上是与同步服务方法相同。二者都可以在没有保护的情况下让网络应用程序屈服会话和上下文状态。"

这意味着什么:"在不保护会话和上下文状态的情况下让网络应用屈服"?他们是说实现SingleThreadModel还不够线程安全吗?因为即使一个servlet一次只能运行一个线程,这也不会阻止其他servlet访问和更改上下文/会话范围的变量

这是正确的。

如果Servlet实现了SingleThreadingModel,那么为什么需要保护会话状态呢?它一次只允许一个线程。我认为,即使您打开一个新的浏览器窗口,servlet也不允许您发出两个请求。

这是不正确的。你可以有另一个选项卡,另一个窗口或其他什么。您可能无法同时访问同一个Servlet,因为您可能被阻止,但您可以访问另一个也访问同一上下文或会话的Servlet。而且,根据API,允许同一个Servlet的多个实例在不同的线程中提供多个响应(唯一的限制是一个实例不能为多个线程提供服务)。

也许他们的意思是,如果不同步上下文/会话状态,一次只有一个线程的不同Servlet仍然可能破坏该状态?

为什么类(静态)变量不是线程安全的?因为所有线程都可以访问和修改(损坏)该值?

静态变量本质上没有什么比实例变量更安全的了。但是您必须了解这些值是如何被保护的,以及SingleThreadModel是如何实现的。如果SingleThreadModel是通过允许Servlet的多个实例来实现的,每个实例都停留在一个线程上,那么静态变量将在所有实例之间共享,因此它们的线程也可以访问。

无论如何,我认为您永远不应该在Servlet类中使用(非最终)静态变量,因为您不能控制Servlet的生命周期。它可以根据容器的要求进行创建、销毁和重新创建。因此,当你下次尝试访问静态变量时,你放在静态变量中的值可能不在那里。你永远不应该使用SingleThreadModel,因为它效率低下,不能真正发挥作用,而且它已经被弃用了很长一段时间。所以你绝对不应该同时使用它们。

让一个网络应用程序屈服

因为对Servlet的service()方法的访问将被同步。这可以通过两种方式实现,(1)阻塞其他request线程,直到当前线程完成service()的执行,[(2)

而不保护会话和上下文状态

因为即使您同步访问实现SingleThreadModel的特定Servlet的service()方法。对sessioncontext的访问不同步。Servlet以外的代码可以自由访问HttpSessionServletContext属性。

他们是说实现SingleThreadModel还不够线程安全吗?

是的,即使是类变量也可能不是线程安全的,如果Container实现了模型,使得每个线程都使用池中的一个空闲Servlet实例。

因为即使一个servlet一次只能运行一个线程,这也不会阻止其他servlet访问和更改上下文/会话范围的变量?

当然。

如果Servlet实现了SingleThreadingModel,那么为什么需要保护会话状态呢?

为了保护存储在HttpSession因为即使一次只能在一个servlet上运行一个线程,这也不会阻止其他servlet访问和更改上下文/会话范围的变量

类(静态)变量不是线程安全

因为它由类的所有实例共享。

为什么类(静态)变量不是线程安全的?因为所有线程可以访问和修改(损坏)该值吗?

正确。如果一个成员是静态的,那么一个线程可以设置一个值,而另一个线程则可以设置不同的值。由于static是共享变量,所以第一个线程设置的值对于另一个线程也是相同的。

Q。"实现SingleThreadModel的效果实际上是一样的作为同步服务方法。两者都可以将网络应用程序膝盖,而不保护会话和上下文状态。"

即使您让一些servlet实现SingleThreadModel,它也只会停止那些试图同时访问该servlet的线程。它不能阻止所有其他未实现SingleThreadModel的servlet访问上下文和会话属性。这是因为上下文属性在整个web应用程序中都是可用的,任何资源都可以访问和修改它们。

最新更新