Google App Script returns array over multiple rows

2019-08-01 23:28发布

Summary

I'm new to Google Apps Script but I've spent quite a bit of time researching and have come up empty. Basically I'm trying to replicate a cross-join functionality of SQL. I have 2 tables, a calendar table with 12 months, and a customer table with 3 customers. The customer table is populated from a Google form, and will have new customers added going forward.

For my reporting, I need the customer data to be at a monthly grain. Therefore I want to cross-join the customer data with the calendar to create a dataset with 36 rows, where each customer has 12 rows, one per month.

Based on other code I've found on stackoverflow, I've gotten close. My issue now is that my two data sets end up displaying on subsequent rows, which seems like an issue with how I'm handling my arrays. I have also tried using push.apply and .concat with the exact same results.

Any help would be appreciated! Workbook can be found here

Also, the calendar table isn't strictly necessary - I just come from a SQL background so my first instinct was to make a calendar table and create a cross join. If you can think of a better way to accept a single row of customer data from a Google form and output X rows with consecutive months and years added, let me know!

Disclaimer: I know this cross-join method would be better handled in a SQL database, and that Google Sheets isn't designed for this. This is a temporary workaround while a better long-term solution is being designed. The customer dataset will likely be less than 100 customers total for this workaround, and is growing at a rate of approximately 1 customer per week.


Calendar Table


Customer Table


Custom Code

function crossJoin(tabl1, tabl2, header) {
 var output = [];
  var days = tabl1;
  var customer = tabl2;
  if(header) {output.push([header[0][1], header[0][0]])};
  for(var i = 1, iLen = customer.length; i < iLen; i++) {
//     output.push(days[i]);
    for(var j = 1, jLen = days.length; j < jLen; j++) { 
      output.push(days[j],customer[i]);

    }
  }
  return output;  
}


Current Output


Desired Output

1条回答
\"骚年 ilove
2楼-- · 2019-08-01 23:59

You can use array methods like concat to achieve the same result.

Code Snippet:

function sqlCrossJoin(arr1, arr2) {
  arr1 = arr1 || [['jan', 1], ['feb', 2]];
  arr2 = arr2 || [
    ['Jane Doe', 1983, 'PortLand', 'Oregon'],
    ['John Smith', 1984, 'San Francisco', 'California'],
  ];
  var output = [];
  arr1.forEach(function(month) {
    arr2.forEach(function(customer) {
      output.push(month.concat(customer));
    });
  });
  return output;
/* Expected Output:
[ [ 'jan', 1, 'Jane Doe', 1983, 'PortLand', 'Oregon' ],
  [ 'jan', 1, 'John Smith', 1984, 'San Francisco', 'California' ],
  [ 'feb', 2, 'Jane Doe', 1983, 'PortLand', 'Oregon' ],
  [ 'feb', 2, 'John Smith', 1984, 'San Francisco', 'California' ] ]*/
}

References:

查看更多
登录 后发表回答