ConcurrentHashMap 原子操作的写法欣赏

文章目录


在阅读 slf4j 源码的时候,发现 BasicMarkerFactory的一个方法实现很有典型意义: 恰好说明了在使用减少
锁争用/CAS的一个技巧.

public class BasicMarkerFactory implements IMarkerFactory {
    private final ConcurrentMap<String, Marker> markerMap = new ConcurrentHashMap<String, Marker>();
    public BasicMarkerFactory() {
    }
    /**
     * Manufacture a {@link BasicMarker} instance by name. If the instance has been 
     * created earlier, return the previously created instance. 
     * 
     * @param name the name of the marker to be created
     * @return a Marker instance
     */
    public Marker getMarker(String name) {
        if (name == null) {
            throw new IllegalArgumentException("Marker name cannot be null");
        }

        /** it really is amazing!!!*/
        Marker marker = markerMap.get(name);
        if (marker == null) {
            marker = new BasicMarker(name);
            // two threads may simultaneously putIfAbsent() ,and only one of them succeeds
            Marker oldMarker = markerMap.putIfAbsent(name, marker);
            if (oldMarker != null) {
                marker = oldMarker;
            }
        }
        return marker;
    }
    
     // 下面这个是笔者加的,当然也能玩...但其实并没有上面的性能好. 但是话说回来,绝大多数场景下, 似乎也够用了..
    // both this one and the one above have the same semantics, while this one will has more race condition
    public Marker myGetMarker(String name) {
        if (name == null) {
            throw new IllegalArgumentException("Marker name cannot be null");
        }
        
        return markerMap.compute(name, (markerName, marker) -> {
            if (marker == null) {
                marker = new BasicMarker(markerName);
            }
            return marker;
        });
    }
	// ... 省略其余代码
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值