通常Servlet只启动一次,web容器simple会为每个用户请求生成一个新线程。比方说,如果我从头开始创建自己的web容器,而不是Thread,我只是将Servlet创建为Singleton。我会遗漏什么吗?我猜,在这种情况下,单例一次只能服务于一个用户请求,而不是多个。
发布于 2010-10-17 01:38:14
通常只启动一次Servlets,web容器simple会为每个用户请求生成一个新线程。
第一种说法是正确的,但第二种说法实际上是错误的。通常,线程在应用程序启动时创建一次,并保存在线程池中。当线程完成其请求-响应处理作业时,它将被返回到池中。这也是在servletcontainer容器中使用ThreadLocal
必须格外小心的原因。
比方说,如果我从头开始创建自己的web容器,而不是线程,我只是将Servlets创建为单例。我会遗漏什么吗?
它们不一定需要遵循单例模式。只需在应用程序启动时创建它们的一个实例,并在应用程序的整个生命周期中将它们保留在内存中,就可以让所有线程访问同一实例。
我猜,在这种情况下,单例一次只能服务于一个用户请求,而不是多个。
这不是真的。只有当您在应用程序范围的锁上同步对单例方法的访问时,才会发生这种情况。例如,将synchronized
修饰符添加到servlet的方法中,或者在将请求委托给servlet的经理的方法中添加synchronized(this)
。
发布于 2010-10-17 01:10:46
JavaEE曾经有一个这样的机制--一个叫做SingleThreadModel
的标记接口,你的servlet可以实现它:
确保servlet一次只处理一个请求。此接口没有方法。
如果servlet实现了此接口,则可以保证在servlet的服务方法中不会同时执行两个线程。servlet容器可以通过同步对servlet的单个实例的访问,或者通过维护servlet实例池并将每个新请求分派到一个空闲的servlet来实现这一保证。
请注意,SingleThreadModel不能解决所有线程安全问题。例如,即使在使用SingleThreadModel servlets时,会话属性和静态变量仍然可以由多个线程上的多个请求同时访问。建议开发人员采取其他方法来解决这些问题,而不是实现此接口,例如避免使用实例变量或同步访问这些资源的代码块。此接口在Servlet API版本2.4中已弃用。
容器可以使用它为每个请求实例化一个新的servlet,或者维护它们的池,如果它们选择的话。
这在Servlet 2.4中被弃用,原因如上所述。同样的原因仍然适用于你的问题。
发布于 2010-10-17 01:08:07
基本上就是这样。
我会质疑创建自己的容器的动机,因为有如此多的容器可用于广泛的目的。
https://stackoverflow.com/questions/3949861
复制相似问题