【问题标题】:Speed Up Find-and-Replace Google Apps Script Function for sheets加快工作表的查找和替换 Google Apps 脚本功能
【发布时间】:2018-12-31 12:40:21
【问题描述】:

我编写了一个非常简单的脚本,该脚本成功地从 Google 电子表格中的一张表中获取信息,并替换同一电子表格中另一张表中的列中的信息,等待满足两个条件:接收行具有相同的“客户ID”和“产品类型”。我说“简单”是因为它很直观,但对计算的要求非常高(运行将近 30 秒!)。

根据我在网上阅读的内容,导致速度变慢的是顺序读取和写入操作。我假设如果我根据两个标准对有问题的工作表进行排序,然后执行一个写入后续行的函数,我也许可以加快速度。我的算法有点弱,所以我还在摸索如何优雅地做到这一点。

有人有什么建议吗?下面是我的原始脚本,我已经确保电子表格折叠空行,因此不会浪费时间进行迭代。

function replaceRawWithRepChanges(receivedSheet) {
  var ss = SpreadsheetApp.openById(receivedSheet);

  var repchanges = ss.getSheetByName('repchanges');
  var rawSheet = ss.getSheetByName('Sheet1');

  var rawTMtoReplace = rawSheet.getRange('P2:P');

  var repCustID = repchanges.getRange('A1:A').getValues();
  var repTM = repchanges.getRange('F1:F').getValues();
  var repCategory = repchanges.getRange('G1:G').getValues();

  var rawCustID = rawSheet.getRange('A2:A').getValues();
  var rawTM = rawSheet.getRange('P2:P').getValues();
  var rawCategory = rawSheet.getRange('U2:U').getValues();

  var repInfo = [repCustID, repTM, repCategory];
  var rawInfo = [rawCustID, rawTM, rawCategory];

  for (var i=0; i < rawInfo[0].length; i++) {
    for (var j=0; j < repInfo[0].length; j++) {
//      var thisRawCust = rawInfo[0][i];
//      var thisRepCust = repInfo[0][j];
      if (rawInfo[0][i].toString() == repInfo[0][j].toString()) {
//        var thisRawCategory = rawInfo[2][i];
//        var thisRepCategory = repInfo[2][j];
        if (rawInfo[2][i].toString() == repInfo[2][j].toString()) {
//          var repvalue = repInfo[1][j];
          rawInfo[1][i] = repInfo[1][j];
//          var newRawValue = rawInfo[1][i];
        }
      }
    }
  }

  return rawInfo[1];
}

【问题讨论】:

  • 这很慢,因为您在外循环中的每一行都经过一次内循环。先建一个索引,然后对照那个索引查找。

标签: algorithm sorting google-apps-script google-sheets


【解决方案1】:

是的,您应该对数据进行排序(也许使用SORT 命令,它确实适用于多列)。然后,使用两个指针,您只需向下移动一次列,而不是检查整个repInfo 以查找rawInfo 中每一行的匹配项。

对信息进行排序后,您的循环可能如下所示:

var i = 0;
var j = 0;
while (i < rawInfo[0].length && j < repInfo[0].length) {
  if (rawInfo[0][i].toString() == repInfo[0][j].toString()) {
    if (rawInfo[2][i].toString() == repInfo[2][j].toString()) {
      rawInfo[1][i]=repInfo[1][j];
      i++;
      j++;
    } else if (rawInfo[2][i].toString() < repInfo[2][j].toString()) {
      i++;
    } else {
      j++;
    }
  } else if (rawInfo[0][i].toString() < repInfo[0][j].toString()) {
    i++;
  } else {
    j++;
  }
}

【讨论】:

    猜你喜欢
    • 2019-02-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-06-01
    • 1970-01-01
    相关资源
    最近更新 更多