线程安全

1.7

思路:

     a.servlet是单实例多线程运行的。因此当多客户端访问时可能会产生线程安全问题。特别是用servlet作购物车时更要注意。

     b.servlet的监听机制。常见监听分类: 1.用于监听与对象自身创建和销毁的时间监听器  2.用于监听与对象中的属性的增加和删除的事件监听。  3.用于监听绑定到httpSession域中的某个对象的状态的时间监听器。(唯一不用在web.xml注册测的监听器)4.钝化和活化概念

      c.整合案例:获取当前在线人数

 

l

Servlet线程安全问题

Servlet是单实例多线程运行的。

解决: 

1.实现 SingleThreadModel 接口 

     该接口指定了系统如何处理对同一个Servlet的调用。如果一个Servlet被这个接口指定,那么在这个Servlet中的service方法讲不会有两个线程被同时执行,当然也就不存在线程安全的问题。

        定义如下:

        Public class HelloWorldServlet extends HttpServlet implements SingleThreadModel   { }

 

2.不使用全局变量,实例变量对所有线程是共有的,会产生并发问题。

               3.尽量使用局部变量,因为局部变量对每个线程都是私有的。

               4. 同步对共享数据的操作

  使用synchronized 关键字能保证一次只有一个线程可以访问被保护的区段

      public void service(ServletRequest request, ServletResponse response)

            throws ServletException, IOException {

                   request.setCharacterEncoding("utf-8");

                   response.setContentType("text/html;charset=utf-8");

                  synchronized (this){   //同步代码块

                         PrintWriter out=response.getWriter();

                         out.println("<html><body>您好,欢迎您来到这个世界上<html><body>");

                         System.out.println("service");

                  }

}

 

 

Servlet监听器

HttpContextListener

 

HttpSessionListener     //可作在线人数统计

HttpServletRequestListener

 

Servlet属性监听器

HttpContextAttributeListener

添加,                 //添加方法执行了两次.第一次是系统的值.第二次是自定义的值

删除,                 //获取的是删除的值

替换。                 //在监听器中得到是替换前的值

 

HttpSessionAttributeListener 

 

HttpServletRequestAttributeListener

Servlet绑定的事件监听

httpSessionBindingListener接口  不需要在webXml中注册

valueBound(HttpSessionBindingEvent event)    //当实现该接口的JavaBean对象被放置到sesion作用于中是调用该方法  

当改变绑定的值时的过程:先绑定新值先调用valueBound,然后接触与老值的绑定 调用valueUnbound

valueUnbound(HttpSessionBindingEvent event)     //当实现该接口的JavaBean对象从sesion作用删除时

重新看11:06的错误

httpSessionActivationListener接口  活化和钝化概念  序列化概念?

要实现的接口: HttpSessionActivationListener,java.io.Serializable

sessionDidActivate(httpSessionEvent se)

 

void sessionDidActivate(HttpSessionEvent se)   // * 活化(把session从硬盘上读取到服务器的内存中)

 

void sessionWillPassivate(HttpSessionEvent se)   // * 钝化(把服务器内存中的session信息存储到硬盘上,已被下次服务器启动,重新读取)

 

java.io.Serializable   //序列化

 

实例:统计当前在线人数列表

//获取远程登录用户的IP

   String ip=request.getRemoteAddr();

 

处理session过期问题:

用HttpSessionListener

 

获取在线人数实现思路:

    a.区分游客和登录用户,因此需要在登录游客的bean中嵌套登录bean

    b.将在线的人添加到游客集合,首先加入到游客中,然后如果登录则将其转入登录用户集合中。实现:在用户访问的首页面设置session的监听绑定。用户的登录信息存放到Map中放入到ServletContext中作全局保留。

    c.设置session对象创建和销毁监听。如果session过期或用户下线则将该用户的信息从map集合中删除。当然session的默认活动时间为30中,所以统计可定会用一定的误差。

 

 

此工程需要的页面

     index.jsp   游客可以访问,登录用户可以访问

     chatper.jsp  只有登录用户才能访问(游客不能访问)

      在WEB-INF/jsp下的 login.jsp   游客可以访问登录用户可以访问

      在WEB-INF/jsp下的 title.jsp  只有登录用户才能访问(游客不能访问)

     

      onlinenum.jsp   --后台管理的jsp页面(登录用户和游客无权访问) --管理员

 

 

     程序执行时,直接访问该index.jsp页面,也就是在地址栏中不需要输入index.jsp

     <welcome-file-list>

        <welcome-file>index.jsp</welcome-file>

      </welcome-file-list>

 

游客流程: 

    index.jsp    转到    WEB-INF/jsp/login.jsp

         <jsp:forward page="/WEB-INF/jsp/login.jsp"></jsp:forward>

        

        

        

      * 服务器启动的时候就执行MyServletContextListener中的

           

                    public void contextInitialized(ServletContextEvent sce) {

                             System.out.println("MyServletContextListener contextInitialized");

                            

                             //获取上下文对象

                             ServletContext sc=sce.getServletContext();

                            

                             //定义集合存放游客和登录用户Map<sessionid,sessionUser>

                             Map  onlineNum=new HashMap();

                  

                             //集合放置到作用域中(范围最大的)

                             sc.setAttribute("onlineNum", onlineNum);

                    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值