Hazelcast中的线程安全计数器地图

时间:2013-09-14 09:50:35

标签: java hazelcast

我需要实现线程安全的群集宽计数器映射,所以我使用Hazelcast使其成为群集范围,但不知道如何使其成为线程安全的,我尝试使用AtomicInteger,但它看起来像一个线程反序列化AtomicInteger进行增量,其他线程可以递增并将其放回映射中。你能为我提一些建议吗?某种最佳做法?我想我可以使用分布式锁实现它,但不确定它是最好的解决方案。

2 个答案:

答案 0 :(得分:7)

我是使用Hazelcast分布式任务完成的,我已实现PartitionAware接口,因此此代码将在计数器所在的节点上执行,因此将执行所有分布式操作(锁定,获取,放置,解锁)在本地,这应该能够实现更高的并发性。

public void track(final ip) {
    try {
        if(ip != null) {
            executor.execute(new IncrementCounterDistributedTask<>(ip, IP_MAP_NAME));
        }
    } catch (RejectedExecutionException ignored) {
    }
}

private static class IncrementCounterDistributedTask<K> implements Runnable, PartitionAware, Serializable {

    private final K key;
    private final String mapName;

    public IncrementCounterDistributedTask(K key, String mapName) {
        this.key = key;
        this.mapName = mapName;
    }

    @Override
    public Object getPartitionKey() {
        return key;
    }

    @Override
    public void run() {
        IMap<K, Integer> map = Hazelcast.getMap(mapName);
        map.lock(key);
        Integer counter = map.get(key);
        if(counter == null) {
            map.put(key, 1);
        } else {
            map.put(key, ++counter);
        }
        map.unlock(key);
    }
}

答案 1 :(得分:1)

我知道这有点旧,但它在我的搜索中成为最佳结果。

我会考虑以下内容。

IAtomicLong counter = client.getAtomicLong("nameOfCounter");
Long incrementedValue = counter.incrementAndGet();