Servlet生命周期

1 生命周期

Servlet程序的生命周期由tomcat服务器控制的。一般情况下,第一次提交请求(request),会创建servlet,也是一个servlet的生命周期的开始。

构造方法 创建servlet对象的时候调用。默认情况下,第一次访问servlet的时候创建servlet对象 只调用1次。证明servlet对象在tomcat是单实例的。

init方法: 创建完servlet对象的时候调用。只调用1次。

service方法: 每次发出请求时调用。调用n次。

destroy方法: 销毁servlet对象的时候调用。停止服务器或者重新部署web应用时销毁servlet对象。只调用1次。

2 servlet自动加载

  默认情况下,第一次访问servlet的时候(即提交申请时)创建servlet对象。如果servlet的构造方法或init方法中执行了比较多的逻辑代码,那么导致用户第一次访问sevrlet的时候比较慢。为了解决这种状况,我们可以设置servlet的自动加载,把创建servlet的时候提前到加载web的时候。只需要在web.xml的servlet配置中加上一项<load-on-startup>即可。

<servlet>
    <servlet-name>LifeDemo</servlet-name>
    <servlet-class>gz.itcast.c_life.LifeDemo</servlet-class>
    <!-- 让servlet对象自动加载 -->
    <load-on-startup>1</load-on-startup>  注意: 整数值越大,创建优先级越低!!
  </servlet>

3 servlet多线程并发问题

注意: servlet对象在tomcat服务器是单实例多线程的。

因为servlet是多线程的,所以当多个servlet的线程同时访问了servlet的共享数据,如成员变量,可能会引发线程安全问题。

解决办法:

1)把使用到共享数据的代码块进行同步(使用synchronized关键字进行同步)

例:每此访问count都会+1,这就涉及多线程和线程安全问题。

 1 public class TheradDemo extends HttpServlet {
 2     
 3     int count = 1;
 4 
 5     public void doGet(HttpServletRequest request, HttpServletResponse response)
 6             throws ServletException, IOException {
 7         response.setContentType("text/html;charset=utf-8");
 8         
 9         synchronized (TheradDemo.class) {//锁对象必须唯一。建议使用类对象
10             response.getWriter().write("你现在是当前网站的第"+count+"个访客");   //线程1执行完  , 线程2执行
11         
12         //线程1还没有执行count++
13         /*try {
14             Thread.sleep(5000);
15         } catch (InterruptedException e) {
16             e.printStackTrace();
17         }*/
18             count++;
19         }
20     }
21 
22 }

2)建议在servlet类中尽量不要使用成员变量。如果确实要使用成员,必须同步。而且尽量缩小同步代码块的范围。(哪里使用到了成员变量,就同步哪里!!),以避免因为同步而导致并发效率降低。 

原文地址:https://www.cnblogs.com/K-artorias/p/7469561.html