我正在尝试批量插入(对象存储在数组列表中,一旦计数可被 10000 整除,我将所有这些对象插入到我的表中。但是这样做需要 4 分钟以上。有没有哪种方法更快?
arr.add(new Car(name, count, type));
if(count%10000==0){
repository.saveAll(arr);
arr.clear();
}
最佳答案
所以这就是正在发生的事情。我最好奇的是看到 Cassandra 内部的表定义。但鉴于您的 Car
构造函数,
new Car(name, count, type)
鉴于这些列名称,我猜测 name
是分区键。
之所以重要,是因为 Cassandra 使用分区键列的哈希来确定数据应写入哪个节点( token 范围)。
当您一次对 10000 辆汽车
进行saveAll
时,您无法保证所有 10000 辆汽车都会到达相同的地点节点。为了解决这个问题,Spring Data Cassandra 必须在幕后使用 BATCH
(或类似的东西)。如果它是一个 BATCH,则本质上是放置一个 Cassandra 节点(指定为“协调器”)来将写入路由到所需的节点。由于 Cassandra 的分布式特性,这永远不会很快。
如果您确实需要存储其中的 10000 个,最好的方法是一次异步发送一个写入。当然,您不希望 10000 个线程同时写入,因此您需要限制(限制)代码中 Activity 线程的数量。 DataStax 的 Ryan Svihla 撰写了几篇文章,详细介绍了如何做到这一点。我推荐这个-Cassandra: Batch Loading Without the Batch - The Nuanced Edition .
tl;博士;
Spring Data Cassandra 的 saveAll
确实不应该用于保存数千次写入。如果我使用 Spring Data Cassandra,我什至不会使用 saveAll
超出两位数,TBH。
编辑
查看此答案,了解有关如何异步使用 Spring Boot/Data 和 Cassandra 的详细信息:AsyncCassandraOperations examples
关于java - saveAll() 太慢了。带 Spring 启动的 Cassandra 数据库。为什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60569288/