【问题标题】:Define multiple ranges in Google Apps Script在 Google Apps 脚本中定义多个范围
【发布时间】:2018-09-06 16:27:46
【问题描述】:

我很难在 GAS 中定义多个范围。

我需要执行以下简单功能:

var dataRange = sheet.getRange(checkRange);
var values = dataRange.getValues();
for (var i = 0; i < values.length; i++) {
  for (var j = 0; j < values[i].length; j++) {
    if (values[i][j] == false) {
      values[i][j] = true; 
    }
  }
}
dataRange.setValues(values);

我的范围实际上是由另一个函数定义的:

var checkRange = [];

  for(var i = 0; i<checkboxes.length; i++) {
  if(checkboxes[i]) {

  checkRange.push('C' + (i+9));
  Logger.log(checkRange);
  }
  }

现在,正如我在日志中看到的那样,所需的范围正在被很好地创建。但是,显然单元格范围所需的 GAS 格式不同,因为我的范围没有定义。此外,我试图找出在 GAS 中编写范围的精确可接受的方式。如果我输入一个像“C9:C11”这样的范围,脚本就可以正常工作。如果我放一个像'C9,C10'或'C9','C10'等这样的列表,它不会。多个范围 ('C9:C11', 'C13:C14') 等也没有......不太清楚我需要如何写这个

【问题讨论】:

标签: javascript jquery google-apps-script range


【解决方案1】:

对可能不相交的Ranges 执行相同的操作最容易使用Rangelist class 完成,并且不需要直接访问成员Ranges。但是,即使操作不同(或有条件),也可以使用 RangeList 来优化电子表格服务的使用,而不是重复调用 Sheet#getRange

从您的代码中,我们可以确定目标是对一组与“真”复选框相关的范围进行操作:

var checkRange = [];
for (var i = 0; i < checkboxes.length; i++) {
  if (checkboxes[i]) {
    checkRange.push('C' + (i+9));
    Logger.log(checkRange);
  }
}

然后(似乎)有条件地更改相关范围的值:

var dataRange = sheet.getRange(checkRange);
var values = dataRange.getValues();
for (var i = 0; i < values.length; i++) {
  for (var j = 0; j < values[i].length; j++) {
    if (values[i][j] == false) {
      values[i][j] = true; 
    }
  }
}
dataRange.setValues(values);

Instantiating a RangeList 是通过 Array 对工作表上范围的字符串引用完成的,例如[ "A1:A10", "C2", "D6:E8", "R5C9:R100C9" ]。因此,您当前的 checkRange 似乎已经具有所需的格式。

您的消费代码如下所示:

const rl = sheet.getRangeList(checkRange);
rl.getRanges().forEach(function (rg) {
  // Assumption: only single-cell ranges, based on the above checkRange code
  if (rg.getValue() == false) // matches false, null, undefined, 0, or ""
    rg.setValue(true);
});

【讨论】:

  • 这正是我想要的!非常感谢您的帮助
【解决方案2】:

从 Google Apps 脚本访问范围时,每个 Range 都必须是一个连续块,您不能选择离散范围(如 C9:C11 和 C13:C14)作为单个 Range 对象。您需要单独访问这些范围。

修改现有代码的一种简单但可能效率低下的方法是遍历您的 checkRange 数组并一次访问它们:

for(var j = 0; j < checkRange.length; j++){
   dataRange = sheet.getRange(checkRange[j]);
   var values = dataRange.getValues();
   for (var i = 0; i < values.length; i++) {
     for (var j = 0; j < values[i].length; j++) {
       if (values[i][j] == false) {
         values[i][j] = true; 
       }
     }
   }
 }

如果每个范围只是一个单元格,则可以将 getValues() 切换为 getValue(),然后就不需要循环遍历 values 数组。

但是,如果您将一个较大的范围作为一系列较小的范围进行访问,那么这将非常低效。最好在可能的情况下使用一些逻辑来构建多单元格范围,或者将整个工作表作为单个范围读取(sheet.getDataRange().getValues()),然后使用数组表示法访问您感兴趣的单元格,之前写回整个数组。

【讨论】:

  • 查看RangeList 类 - 在过去 6 个月内添加。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-05-28
  • 1970-01-01
  • 2016-03-23
  • 1970-01-01
相关资源
最近更新 更多