Google Apps Script中Range报错:行数至少为1的问题求助
问题分析与修正方案
错误原因
清空目标区域时的范围无效
当目标工作表(Target)只有表头行(第1行)时,targetSheet.getLastRow() - 1结果为0,此时getRange(2,1,0,28)会因为行数为0触发报错,这就是你看到的Exception: The number of rows in the range must be at least 1。核心判断逻辑全错
- 循环遍历每一行,但判断条件里一直用
dataValues[0][xxx],也就是只检查第一行的列值,完全没处理当前循环的行; - 要检查的是24、25、26列,对应数组索引应该是23、24、25(数组索引从0开始,第1列对应索引0),代码里用了24、25、26、27,列数完全不对;
- 用
==判断等于'name',不符合“包含单词'name'”的需求,应该用includes()方法。
修正后的代码
function onOpen() { SpreadsheetApp.getUi() .createMenu('Admin') .addItem('Copy name rows', 'copyNameRows') .addToUi(); } function copyNameRows() { const sourceSheet = SpreadsheetApp.getActive().getSheetByName('Source'); const targetSheet = SpreadsheetApp.getActive().getSheetByName('Target'); const dataValues = sourceSheet.getDataRange().getValues(); // 修正清空逻辑:先判断目标表是否有数据行,再清空 const targetLastRow = targetSheet.getLastRow(); if (targetLastRow > 1) { targetSheet.getRange(2, 1, targetLastRow - 1, 28).clear(); } let currentTargetRow = 2; // 遍历每一行(若表头不需要检查,可把i=0改成i=1跳过表头) for (let i = 0; i < dataValues.length; i++) { const row = dataValues[i]; // 检查24、25、26列(对应索引23、24、25)是否包含'name'(不区分大小写) const hasName = row[23]?.toString().toLowerCase().includes('name') || row[24]?.toString().toLowerCase().includes('name') || row[25]?.toString().toLowerCase().includes('name'); if (hasName) { // 复制当前行到目标表 sourceSheet.getRange(i + 1, 1, 1, 28).copyTo(targetSheet.getRange(currentTargetRow, 1)); currentTargetRow++; } } }
额外优化建议(大数据量适用)
逐行复制效率较低,如果数据量很大,可以改用批量写入方式:
// 批量写入版本的copyNameRows function copyNameRowsBatch() { const sourceSheet = SpreadsheetApp.getActive().getSheetByName('Source'); const targetSheet = SpreadsheetApp.getActive().getSheetByName('Target'); const dataValues = sourceSheet.getDataRange().getValues(); // 清空目标表数据行 const targetLastRow = targetSheet.getLastRow(); if (targetLastRow > 1) { targetSheet.getRange(2, 1, targetLastRow - 1, 28).clear(); } // 收集符合条件的行 const filteredRows = dataValues.filter(row => { return row[23]?.toString().toLowerCase().includes('name') || row[24]?.toString().toLowerCase().includes('name') || row[25]?.toString().toLowerCase().includes('name'); }); // 如果有符合条件的行,批量写入 if (filteredRows.length > 0) { targetSheet.getRange(2, 1, filteredRows.length, filteredRows[0].length).setValues(filteredRows); } }
内容的提问来源于stack exchange,提问作者debaron
相关产品推荐
相关产品推荐

