【发布时间】:2021-09-07 15:44:46
【问题描述】:
我正在编写一个脚本来将学生分成干预组,并且我希望结果表按字母顺序排序。我还需要在要添加的新行中添加复选框。我的代码有效,但它似乎非常低效,因为我添加了带有复选框的新行,获取新数据范围,对其进行排序,然后将其重写到电子表格中。任何清理它的帮助将不胜感激。
function filterToGroup(sheet, student, value) {
var oldDataRange = sheet.getDataRange();
var oldDataValues = oldDataRange.getValues();
if (value === true) {
// Add new row to spreadsheet based on filter requirements
sheet.appendRow([student]);
// Insert checkboxes after the name to complete the row
sheet.getRange(sheet.getLastRow(), 2, 1, oldDataValues[0].length).insertCheckboxes();
// Get the sheet values with the new row
var newRange = sheet.getRange(2, 1, sheet.getLastRow() -1, oldDataValues[0].length);
var newValues = newRange.getValues();
// Sort them
var sortedNewValues = newValues.sort(function(a,b) {return a[0] > b[0] ? 1 : -1});
// Write the newly sorted values back to the sheet
newRange.setValues(sortedNewValues);
} else {
for (i = 1; i < oldDataValues.length; i++) {
if (student == oldDataValues[i][0]) {
sheet.deleteRows(i+1, 1);
break;
}
}
}
当老师点击“Phonics”下的复选框时,我希望学生添加到带有复选框的“Phonics”表中:
启动filterToGroup函数的函数是
function onEdit(e) {
var editedSheet = e.range.getSheet().getSheetName();
var editedColumn = e.range.getA1Notation().charAt(0);
var editedValue = e.range.getValue();
var student = rosterValues[e.range.getRow() -1][0];
if (editedSheet == "Roster") {
if (editedColumn == "E") filterToGroup(phonicsSheet, student, editedValue);
if (editedColumn == "G") filterToGroup(phonologicalAwarenessSheet, student, editedValue);
if (editedColumn == "H") filterToGroup(letterNamesAndSoundsSheet, student, editedValue);
}
}
我想我已经弄清楚了。它仍然不是超级快,但它不到一秒钟并且不会两次写入工作表。一旦我发现我可以在事后插入复选框,它真的很有帮助。这是新代码:
function filterToGroup(sheet, student, value) {
var oldDataRange = sheet.getDataRange();
var oldDataValues = oldDataRange.getValues();
if (value === true) {
// Check if the student is the first to be added;
// If so, just append row
if (oldDataValues.length === 1) {
phonicsSheet.appendRow([student]);
// Run the new addCheckboxes function to add checkboxes to row
addCheckboxes(phonicsSheet, 1, oldDataValues[0].length -1);
} else {
// If data has already been added, remove header row
oldDataValues.shift();
// Create a new array with the student data and false values
var newStudent = Array.apply(null, Array(oldDataValues[0].length -1).map(_ => false));
newStudent.unshift(student);
// Add the new student to the data and sort
oldDataValues.push(newStudent);
var newDataValues = oldDataValues.sort();
// Write the sorted object to the sheet
sheet.getRange(2, 1, newDataValues.length, newDataValues[0].length).setValues(newDataValues);
// Add checkboxes to the sheet (existing true values will still be recognized)
addCheckboxes(sheet, newDataValues.length, newDataValues[0].length -1);
}
} else {
for (i = 1; i < oldDataValues.length; i++) {
if (student == oldDataValues[i][0]) {
sheet.deleteRows(i+1, 1);
break;
}
}
}
}
function addCheckboxes(sheet, numRows, numCols) {
sheet.getRange(2, 2, numRows, numCols).insertCheckboxes();
}
【问题讨论】:
-
我假设您在循环中调用 filterToGroup。如果这样做,那肯定会非常低效。我的建议是读取所有值,添加行,进行更改并将所有内容写回工作表。最终,您将进行一次读取和一次写入操作。要以这种方式添加复选框,您需要联系工作表服务/API 并在调用 developers.google.com/sheets/api/reference/rest/v4/spreadsheets/… 之前准备一批
-
它不是循环的一部分。它在单击复选框时触发。如果该框为真,它会将学生发送到新工作表并按字母顺序对其进行排序。如果为假,则删除学生所在的行。是复选框让我失望。我知道如何仅使用数据来执行此操作,但设置复选框很困难。
-
我在原始帖子中添加了其他信息。
-
请同时提供样张,以便更好地把握您的顾虑。
标签: google-apps-script google-sheets