,使得其同时处理客户请求的吞吐量降低,而且很多客户处于阻塞状态。另外为保证主存内容和线程的工作内存中的数据的一致性,要频繁地刷新缓存这也会大大地影响系统的性能。所以在实际的开发中也应避免或最小化Servlet中的同步代码;在Serlet中避免使用实例变量是保证Servlet线程安全的最佳选择。Java内存模型也可以知道,从方法中的临时变量是在栈上分配空间,而且每个线程都有自己私有的栈空间,所以它们不会影响线程的安全。补充:
fservlet存在的多线程问题实例变量实例变量是在堆中分配的并被属于该实例的所有线程共享,所以不是线程安全的JSP系统提供的8个类变量JSP中用到的OUTREQUESTRESPONSESESSIONCONFIGPAGEPAGECONXT是线程安全的APPLICATION在整个系统内被使用所以不是线程安全的局部变量局部变量在堆栈中分配因为每个线程都有它自己的堆栈空间所以是线程安全的静态类静态类不用被实例化就可直接使用也不是线程安全的
外部资源在程序中可能会有多个线程或进程同时操作同一个资源如多个线程或进程同时对一个文件进行写操作此时也要注意同步问题使它以单线程方式执行这时,仍然只有一个实例,所有客户端的请求以串行方式执行。这样会降低系统的性能对于存在线程不安全的类如何避免出现线程安全问题1、采用sy
chro
ized同步。缺点就是存在堵塞问题。2、使用ThreadLocal实际上就是一个HashMap这样不同的线程维护自己的对象,线程之间相互不干扰。
ThreadLocal的设计首先看看ThreadLocal的接口:Objectget返回当前线程的线程局部变量副本protectedObjecti
itialValue返回该线程局部变量的当前线程的初始值voidsetObjectvalue设置当前线程的线程局部变量副本的值ThreadLocal有3个方法,其中值得注意的是i
itialValue,该方法是一个protected的方法,显然是为了子类重写而特意实现的。该方法返回当前线程在该线程局部变量的初始值,这个方法是一个延迟调用方法,在一个线程第1次调用get或者setObject时才执行,并且仅执行1次。ThreadLocal中的确实实现直接返回一个
ull:
fprotectedObjecti
itialValueretur
ullThreadLocal是如何做到为每一个线程维护变量的副本的呢?其实实现的思路很简单,在ThreadLocal类中有一个Map,用于存储每一个线程的变量的副本。比如下面的示例实现:publicclassThreadLocalprivateMapvaluesCollectio
ssy
chro
izedMap
ewHashMappublicObjectgetThreadcurThreadThreadcurre
tThreadr