最近公司大牛在电话面试某位来我们公司面试的员工的时候问了那么一些问题,引起了本人的深思,因为自己也不会。
我们公司大牛电话问:看你简历上写的对servlet比较熟悉,那么请问你知道servlet是线程安全的还是线程不安全的呢。
被面试的人回答:线程不安全的。
大牛问:为啥是线程不安全的呢。
被面试者回答:提交效率,如果是线程安全的,那么效率低下(比如说加锁效率就比较低下)
大牛又问:还有吗?
被面试者回答:不知道了。
大牛于是不耐烦了。
回来仔细思考觉得自己也回答不出这个问题,于是回来百度一波,与大家共勉。不能说提高大家的编写代码的水平,但是也算是对java后台中很多东西为什么这么写有了一个了解,理解不是很深入,也许后面我会有更加深入的理解。
要理解这个首先要理解servlet的生命周期
init() -> service() -> destory() 三个 过程
在javaweb的开发过程中所有的东西都是基于servlet来进行开发的,对于get,post,delete,put等请求都是在service中进行判断,同时格式化返回相应的结果。同时servlet的一个很重要的特性也就是单例模式。也就是在同一时刻后台程序只有一个sevlet在运行。
我们要知道tomcat的最大线程数是150,同时可以等待100个线程。那么问题来了,当并发超过一个时,tomcat就会多个线程去访问servlet程序。而|servlet只有一个。那么在这个情况下试问如果servlet是线程安全会怎么样。
我的想法是servlet如果本身要是线程安全的话,那么就要给servlet加锁,加锁那么岂不是不能并发了,java最大的好处是高并发,如果没了高并发这个特点,估计早就死在了历史里面,都不会出现了。
这个也是为什么我们在开发的过程中要注意实例变量和static设置的变量的原因。因为实例变量也就是全局变量如果在并发的情况下是会发生数据不安全的问题的,所以尽量把实例变量变成局部变量。如果必须要用记得上锁。同时锁住的话呢记得采用最小代码路径,以便提高代码的性能。
通过理解透彻这个问题,我们可真的就知道为什么开发中要注意实例变量和static变量了。与君共勉