在网上看了一些文章,感觉理论性太强了,现在我们先简单说一下Servlet的生命周期,然后用代码进行验证。
当游览器访问服务器时,服务器对url进行解析,如果游览器要的不是静态资源,服务器就根据URI访问对应的Servlet,以tomcat为例,tomcat首先会判断Servlet是否被实例化了,因为在默认情况下Servlet是单例的,也就是只会被创建一次(等会代码演示),如果没有被创建,也就表示这是第一次访问,然后tomcat就会创建对应的Servlet的实例对象,然后放入类似于HashMap的容器中进行管理,并且调用Servlet的init方法,然后再调用Servlet的service方法。如果不是第一次,那么tomcat就会直接调用service方法。最后,当tomcat关闭时,Servlet就会被销毁,但是销毁前会调用destroy方法。下面用图和代码进行演示。
下面给出Servlet生命周期中所遵循的过程
- Servlet 初始化后调用 init () 方法。
- Servlet 调用 service() 方法来处理客户端的请求。
- Servlet 销毁前调用 destroy() 方法。
- 最后,Servlet 是由 JVM 的垃圾回收器进行垃圾回收的。
图示大致为
我们首先来验证上面所说的Servlet是单例的,也就是只会创建一次,测试代码如下
import javax.servlet.*;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.*;
import java.io.IOException;
@WebServlet("/single")
public class SingleServlet extends HttpServlet {
private int count = 0;
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
System.out.println("当前servlet访问次数为:" + ++count);
}
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doGet(request, response);
}
}
我们在代码中定义了一个私有的属性count来记录访问次数,如果每次访问的输出都是1,那么我们的Servlet就不是单例的,如果输出的count一值加1,那么就是单例的,我们启动服务器来访问一下,看控制台输出情况。
我们访问了4次,发现访问次数每次都增加,也验证了Servlet是单例的,既然是单例,那么我们就可以肯定的知道该类只会被初始化一次,又因为init方法在创建时才会调用,所以init也只会调用一次。同理,destroy也是。我们还是设计一个test来说明,代码如下
import javax.servlet.*;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.*;
import java.io.IOException;
@WebServlet("/life")
public class LifeServlet extends HttpServlet {
@Override
public void init() throws ServletException {
System.out.println("调用了init方法");
}
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("调用了service方法");
}
@Override
public void destroy() {
System.out.println("调用了destroy方法");
}
}
我们启动服务器,并且进行第一次访问
果然,第一次访问先创建Servlet实例对象,然后调用init方法,然后调用service方法,我们继续访问第二次。
和我们想的一样,因为已经存在该Servlet的实例对象了,所以直接调用service方法,我们多访问几次试一下。
发现确实是只调用了service方法。最后我们关闭tomcat。
果然,这个也和想的一样,Servlet在服务器关闭时被销毁,销毁前调用destroy方法。
到此,我们的Servlet生命周期就已经演示完了,想必经过演示后,对Servlet的生命周期又有了更深刻的认识,最后,给出w3c上的一张Servlet生命周期的架构图,再一次加深对Servlet生命周期的认识。
以上仅为个人看法,如有误请在评论中指出,我看见就会进行修改。如果觉得这篇文章对你有帮助,那就点个赞支持一下吧!!!