令人瞠目结舌的空指针异常

   工作久了,就会遇到各种稀奇古怪的bug,这不今天就遇到一个最普通的空指针异常,奇怪的是它出现的位置怎么看也不可能会出现空指针异常。

  1. 用arthas定位到,出现异常的方法是HashSet里面的isEmpty方法。这个方法就一行,只有一个可能就是map为null。
  2. HashSet里面的map怎么会被设置成null呢,并没有方法能把map设置成null,那就只能是非常规手段(反射)造成的,通过搜查,并没有这样的代码。那还有一个可能就是并发问题,这个set集合是一个对象里面的属性,这个对象是个缓存,多个线程都能获取到同一个对象,所以是有线程安全问题的。问过AI,也是有并发问题的可能。
  3. 搜查完使用这个属性的地方,并没有对这个属性进行修改或者重新指向。
  4. 最后发现是get方法里面的问题
        private HashSet set = new HashSet();
    
        public HashSet getSet() {
            if (CollUtil.isEmpty(set)) {
                set = new HashSet();
            }
            return set;
        }

    getSet方法被多个线程调用,set属性刚好是空集合,所以每次都会执行set = new HashSet();这一行代码,当一个线程正在执行CollUtil.isEmpty(set)这个方法,另一个线程正在执行set = new HashSet()这个方法,就有可能出现HashSet里面的isEmpty方法空指针异常。

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值