java - GAE 物化规模巨大?进口

标签 java google-app-engine google-cloud-datastore

我需要将大约 1,000,000 条记录导入到数据存储中。更重要的是,我想将其中一些记录合并为一个记录。到目前为止,我尝试过的所有操作都需要很长时间,并且如果后端中途终止任务并在另一台计算机上重新启动它,则不太适合恢复。

我的第一次尝试是在每次插入之前查询数据存储,以将数据添加到现有匹配记录或插入新记录。

Crops local = // read from CSV
for (...)
{
  Crops db = ObjectifyService.ofy().load().type(Crops.class).
    id(local.country + "_" + local.cropType + "_" + 
    new Integer(local.year).toString()).now();

  if (db == null)
  {
    db = local;
    crops.put(composite, db);
  }
  else
  {
    // add additional data to db
  }
  ObjectifyService.ofy().save().entity(db).now();
}

完成此任务的预计时间为 13 小时。

所以我尝试在本地聚合数据

Crops local = // read from CSV
HashMap<String, Crops> crops = ...
for (...)
{
  String composite = local.country + "_" + local.cropType + "_" + 
    new Integer(local.year).toString();
  Crops db = crops.get(composite);

  if (db == null)
  {
    db = local;
    crops.put(composite, db);
  }
  else
  {
    // add additional data to db
  }
}
ObjectifyService.ofy().save().entities(crops.values()).now();

这会导致程序由于堆变得太大而终止。

我工作的一个变体是将聚合数据分割成 1000 条记录的 block 来存储它们。

Iterator<Crops> sit = crops.values().iterator();
List<Crops> list = new ArrayList<Crops>(1000);
i = 0;
while (sit.hasNext())
{      
  list.add(sit.next());
  i++;
  if (i >= 1000)
  {
    ObjectifyService.ofy().save().entities(list).now();
    list.clear();
    i = 0;
  }
}
ObjectifyService.ofy().save().entities(list).now();

但完成此任务的预计时间为 80 小时。

我想尝试的下一件事是并行插入这些 1000 个 block ,而不是顺序插入。

但在我在这上面浪费更多时间之前,我想问一下我是否走在正确的道路上,或者我的做法完全错误。也许在 13 小时内不可能获得这样的导入?

tl;博士

将大型数据集导入数据存储区的最快方法是什么?

最佳答案

  1. 看看MapReduce - 它是专门为可以分割成更小的 block 的大量作业而设计的。

  2. 不需要检查实体是否已存在,除非该实体中存在某些数据,如果覆盖它就会丢失。如果可以安全地覆盖它,只需插入您的实体即可。这应该可以将您的时间减少一半或更多。

  3. 批处理数据库调用将显着加快速度。

  4. 我不知道 local.year 是什么类型,但如果它是 int,你可以简单地这样做:

    String composite = local.country + "_" + local.cropType + "_" + local.year;
    

关于java - GAE 物化规模巨大?进口,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26958585/

相关文章:

java - 使用 SecurityManager 的性能损失是多少(如果有的话)

java - 部署在tomcat上的spring boot无法启动

java - 对象数组作为 Rest 服务中的参数

java - 如何将 Firestore 数据导出到 Google Cloud Storage?

python - 在 Google App Engine 中创建用户并以简单的方式进行迁移

google-app-engine - "datastore: internal error: server returned the wrong number of entities"检索不存在的对象时

java - RxJava : Watch custom class

java - 如何在 google app engine 中创建常驻实例?

node.js - AppEngine Standard 和 NodeJS 的本地开发服务器

javascript - 如何在app引擎上用python实现 Stripe 自定义按钮