如何让apache点燃使用可用于过滤缓存的所有CPU功率?

时间:2016-04-29 18:19:30

标签: java multithreading performance ignite

我试图强制Apache Ignite 1.5.0.final使用单个节点上可用的所有CPU电源并行处理本地缓存数据但是我可以清楚地看到它没有使用所有可用的核心。

缓存创建如下:

    CacheConfiguration<Integer, MyObject> cfg = new CacheConfiguration<Integer, MyObject>();
    cfg.setSwapEnabled(false);
    cfg.setName(CACHE_NAME);
    cfg.setCacheMode(CacheMode.PARTITIONED);
    cfg.setMemoryMode(CacheMemoryMode.ONHEAP_TIERED);
    cfg.setBackups(0);
    cfg.setCopyOnRead(false);
    this.cache = ignite.getOrCreateCache(CACHE_NAME);

CPU使用情况看起来只有一个线程正在进行工作。当我将实现切换到ArrayList时 - 不使用Ignite,CPU使用率达到400%。

这段代码用于过滤缓存:

            IgniteCache<Integer, MyObject> cache = ignite.getOrCreateCache(CACHE_NAME);
            Spliterator<Entry<Integer, MyObject>> split = cache.localEntries().spliterator();
            Stream<MyObject> stream = StreamSupport.stream(split, true).map( entry -> entry.getValue());    
            aggregate.setCount(stream.filter(new SomePredicate()).count());

使用Ignite运行时进行了一些分析,发现一次只有一个Runnable线程,而ArrayList有3个或4个进行工作。

非常感谢,

巴特

1 个答案:

答案 0 :(得分:0)

localEntries返回内部Ignite数据结构的迭代器,所以我认为不可能在没有额外支持的情况下使用Java流API拆分它。但是您可以使用允许迭代特定分区的ScanQuery并行化任务。获取本地分区号列表,为每个分区创建单独的查询,并在单独的线程中执行查询。代码如下所示:

// Get list of local partitions.
int[] partitions = ignite.affinity(CACHE_NAME).allPartitions(ignite.cluster().localNode());

// For each partition submit a task to a thread pool.
for (final int partition : partitions) {
    executor.submit(new Runnable() {
        @Override public void run() {
            ScanQuery<Integer, MyObject> query = new ScanQuery<>();

            query.setPartition(partition);
            query.setLocal(true);

            QueryCursor<Cache.Entry<Integer, MyObject>> cursor = cache.query(query);

            for (Cache.Entry<Integer, MyObject> entry : cursor) {
                // ...
            }
        }
    });
}