Сравните два столбца A на двух листах и ​​сгенерируйте уникальные значения на листе 1, используя скрипт Google Apps. - PullRequest
0 голосов
/ 12 июня 2019

У меня есть два листа с дюжиной столбцов и тысячами строк. Каждый лист имеет столбец A, который содержит уникальный идентификатор. Я хочу сравнить два листа, используя только столбец A в качестве точки сравнения, и создать третий лист, содержащий целые строки с уникальным идентификатором, который находится на листе 1, но не на листе 2.

Вот визуализация:

Sheet 1
+---+--------+-----+-----+
|   |   A    |  B  |  C  |
+---+--------+-----+-----+
| 1 | 1111   | xxx | zzz |
| 2 | 2222   | yyy | zzz |
| 3 | 2222-1 | zzz | xxx |
| 4 | 3333   | xxx | yyy |
+---+--------+-----+-----+
Sheet 2
+---+------+-----+-----+
|   |  A   |  B  |  C  |
+---+------+-----+-----+
| 1 | 1111 | xxx | zzz |
| 2 | 2222 | yyy | zzz |
| 3 | 3333 | xxx | yyy |
+---+------+-----+-----+

Желаемая функция сравнила бы Лист 1 и Лист 2, используя A в качестве основы, и функция указала бы, что ячейка sheet1 [A2] уникальна, она скопирует всю строку 2: 2, а затем вставит ее в недавно сгенерированный лист. Содержание B и C не имеет значения в сравнении.

Я хотел создать цикл, который бы сравнивал каждую ячейку в столбце A для обоих листов, и если sheet1.A [n]! = Sheet2.A [n], но он работал бы, только если оба листа имели одинаковые длины.

В указанном выше случае цикл, который я создал с помощью пользователя, Купера обнаружил, что строка 3 уникальна, и после этого все будет уникальным из-за смещения.

Листы всегда будут разной длины, и уникальные символы могут появляться в разных местах (т. Е. 2222-1 может закончиться в следующий раз, когда я сделаю сравнение в строке 5).

function compareSheetDrop(input) {

var ss = SpreadsheetApp.getActiveSpreadsheet();

//establish first sheet and get its data range
var dropSheet = ss.getSheetByName("Drop (2)");
var dropRange = dropSheet.getRange(2, 1, dropSheet.getLastRow() - 1, dropSheet.getLastColumn());
var vA1 = dropRange.getValues();

//establish the sheet with new data and get its data range
var compareSheet = ss.getSheets()[4];
var compareRange = compareSheet.getRange(2, 1, compareSheet.getLastRow() - 1, compareSheet.getLastColumn());
var vA2 = compareRange.getValues();

//establish the sheet with results
var resultSheet = ss.getSheetByName("ADQA");

for (var i = 0; i < vA1.length; i++) {

//i've tried to make the loop stop once it encounters a blank cell to avoid a type error, but doesn't work
    if (vA2[i][0] === '' || vA1[i][0] === '') {
        break;
        }

    else if (vA1[i][0] != vA2[i][0]) {
    Logger.log(vA1[i][0] + " & " + vA2[i][0]);
            resultSheet.appendRow(vA2[i]);
        }
    }
}

Даже если мой код не дает желаемых результатов, с ним также есть две проблемы: Он зацикливается, пока не появится TypeError: Cannot read property "0" from undefined., с которым я пытался бороться, но безрезультатно.

Более того, метод appendRow не записывает данные в уже существующие ячейки, а вставляет строку перед уже существующими - после трехкратного запуска моего тестового сценария таблица результатов содержала тысячи столбцов и была едва работоспособна.

Любые идеи, как я мог бы изменить свой существующий код, чтобы получить то, что я хочу, избегая при этом вышеупомянутых проблем? Или это требует совершенно нового подхода? Есть предложения?

1 Ответ

0 голосов
/ 12 июня 2019

Поток:

  • Используйте Array#map, чтобы получить весь лист 1 col A в массиве (скажем, a).
  • Используйте Array#filter для фильтрации листа2 по массиву выше.
  • Использовать отфильтрованный массив непосредственно в setValues ​​()

Отрывок:

var a1 = [[1,'x','z'],[2,'y','z'],[3,'m','z'],['2-1','x','z']];//sheet1ValuesArr
var a2 = [[1,'x','z'],[2,'y','z'],[3,'m','z']];//Sheet2ValuesArr
var a = a2.map(function(e){ return e[0]}); //Sheet2Col A : [1,2,3]
var filteredArr = a1.filter(function(e){return !~a.indexOf(e[0])});
console.log(filteredArr); //to use in setValues
resultSheet.getRange(1, 1, filteredArr.length, filteredArr[0].length).setValues(filteredArr)

Ссылки:

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...