Google App Script Array - Why Return Undefined? - arrays

I have written something like this on Google App Script:
var crossup = [];
var i;
var name_cell;
var cross_up_cell;
cross_up_cell = sheet.getRange(2, 1);
for (i = 1; i <= 12; i++) {
var ticker;
var value1;
ticker = name_cell.offset(0, i).getDisplayValue();
value1 = cross_up_cell.offset(0, i).getDisplayValue();
if (value1=="YES") {crossup.push(ticker)};
}
What I had in mind: I thought I was going to output an array of value1 with the value "ticker" assign by getDisplayValue(), but as I output the array, it turns out that I received a series of "undefined" as output.
To be exact, whenever value1 is really "YES" on my Google SpreadSheet, the if statement did "push" "ticker" into the crossup array, but instead of pushing back the display value, it pushed back "undefined"...
Help!!! How come?

The var name_cell isn't set.
Use code below, where
cross_up_cell = sheet.getRange(2, 1);
sheet = SpreadsheetApp.getActiveSheet();
cross_up_cell = sheet.getRange(2, 1);

You never fully define name_cell, so your offset method for ticker returns an undefined cell/range, which then gets pushed to your crossup array.
Your syntax is a bit odd with initializing and assigning variables, so I've rewritten the snippet you posted:
function myFunction() {
var sheet = SpreadsheetApp.openById(*****).getSheetByName("PASTEVALUE"), //get sheet
crossup = []; //initialize empty crossup array
//get the display values in row 2 up to column 12
var values = sheet.getRange(2, 1, 1, 12).getDisplayValues()[0];
//get the display values in row 3 up to column 12, assuming they are in row 3
var ticker = sheet.getRange(3, 1, 1, 12).getDisplayValues()[0];
//initialize increment in for loop, i's value goes from 0 to values.length-1 (the array's full index range)
for (var i in values) {
//if the value in row 2, column "i" is "YES", push the value of row 3, column "i" to the crossup Array
if (values[i] == "YES") crossup.push(ticker[i]);
}
//do stuff with crossup...
}
Instead of incrementally offsetting cells, you can use getDisplayValues() of an extended Range (full row or column, or multiple rows and columns) to get a 2D array, which I think is much quicker to increment through.
Either defining name_cell in your example or editing to make the syntax changes should fix your problem. Let me know if you have any problems or questions.

Related

Math with typescript array - Angular

I'm really confused about how to approach this:
I have an array like this:
arr=["X12","Z1","Y7","Z22","X4","X8"]
I wish to perform mathematical functions on the elements such that:
Each element starting with "X" will have a fixed value 5, hence if there are 3 elements starting with "X" inside the array arr, it should go as : (fixed value of X) multiplied by (No. of "X" element occurrences inside array) = 5x3 = 15.
I tried something like this to calculate the no. of occurrences of "X" element but it doesn't work.
var xcounter = 0;
calculate(){
this.arr.forEach(element => {
if(this.arr.includes("X"))
{
this.xcounter++; //this doesn't give me no. of X element occurrences though.
}
});
}
What would be a clutter-free way to do this?
You could try to use array filter() with string startsWith() method.
var arr = ["X12","Z1","Y7","Z22","X4","X8"];
var valueX = 5;
var occurencesX = arr.filter(item => item.startsWith('X')).length;
console.log(occurencesX * valueX);
You can also try this
loop in to your array
Find how many time you found values which has X in starts
var arr=["X12","Z1","Y7","Z22","X4","X8"]
let total = 0
arr.forEach(
(row) =>{
total = row.startsWith('X')? total + 1 : total
}
)
console.log(total * 5)

Compare 2 arrays and get row number of matching value in GAS

I have 2 sheets, sheet4 contains a range of dates, in this case 20 of them, sheet1 contains 7 of these dates from sheet4 after I filtered out the duplicates. I need to compare these two arrays and get the row number of the matching values on sheet1.
Sheet1 values:
Sheet4 values:
I need to check which row number on sheet1 is corresponding to the value on sheet4. For example, "F1" on sheet4 would give me the value of 2 (as of row 2), and "F5" "F6" and "F7" which are all 07/11/2019 06:10 would all give me the value of 3.
I need the corresponding row numbers in an array as well, so I can use them later on next to the sheet4 dates.
I can't seem to figure it out how to write the code for it, as the arrays are different length.
Edit: My code so far. It returns the row numbers of sheet one multiple times, in an order, like: 1,2,3,4,5,6,7,1,2,3,4,5,6,7,1,2,3,4,5,6,7,1,2,3,4,5,6,7,1,2,3,4,5,6,7
var sheet4Array = ' array on sheet 4 column F';
var sheet1Values = 'values on sheet 1 in an array';
var rowMM = ' row numbers on sheet 1';
var sheet1Array = []; // sheet 1 array
var ss1Arr = [];
for (var p = 0; p < sheet4Array.length; p++) {
for (var s = 0; s < sheet1Values.length; s++) {
if (sheet4Array[p].indexOf(sheet1Values[s])) {
var sheet1A = rowMM[s];
sheet1Array .push(sheet1A);
}
}
}

How to append array data to spreadsheet column at once using Google Script?

I am trying to append data of addArray[] to end of column A at once. However, my array is not multidimensional to be able to use this method:
this is how i add to array:
var toAdd=[];
var thisurl="red apple http://awebsite.com/1.jpg";
toAdd.push(thisUrl);
And this is the way i would like to append the array at once
function AddToSpreadsheet()
{
var data = SpreadsheetApp.getActiveSheet().getRange('A12:A').getValues();
var toAdd=["red apple http://awebsite.com/1.jpg",
"green apple http://1awebsite.com/2.jpg",
"red apple http://1awebsite.com/3.jpg",
"rotten apple http://rottenApple.com"];
if(toAdd.length > 0){
for(i = 0; i < data.length; ++i){
if(data[i][0] == ""){break;}
}
SpreadsheetApp.getActiveSheet().getRange(12+i, 1, toAdd.length, 1).setValues(toAdd);
}
}
if i use this above code i get this error:
Cannot convert Array to Object[][]. (line
My addArray is not multidimensional array ! How i can convert it to multidimensional array like the following example so i can use the above code ?
Multidimensional array example :
var toAdd=[["red apple http://awebsite.com/1.jpg"],
["green apple http://1awebsite.com/2.jpg"],
["red apple http://1awebsite.com/3.jpg"],
["rotten apple http://rottenApple.com"]];
Edit: I converted the array at start and worked!
var values_array=["red apple http://awebsite.com/1.jpg",
"green apple http://1awebsite.com/2.jpg",
"red apple http://1awebsite.com/3.jpg",
"rotten apple http://rottenApple.com"];
var toAddArray = [];
for (i = 0; i < toAdd.length; ++i){
toAddArray.push([toAdd[i]]);
}
...........
and this way i inserted the whole new array to column A:
............
SpreadsheetApp.getActiveSheet().getRange(12+i, 1, toAddArray.length, 1).setValues(toAddArray);
}
You need to "transpose" the array.
You can do that by creating a new array and appending the values as arrays with one value.
before you call setValues(toAdd) try
var toAddArray = [];
for (i = 0; i < toAdd.length; ++i){
toAddArray.push([toAdd[i]]);
}
And replace the set values call with
SpreadsheetApp.getActiveSheet().getRange(12+i, 1, toAdd.length, 1).setValues(toAddArray);
The set values function needs a matrix as an input. Since there is no native matrix it requires an array of arrays where each of the subarrays have the same length and contain no arrays.
Each array within the "matrix" is a row and each element of each arrays goes into a column.
If you want one column of rows from a one dimensional array you need an array with one-element arrays. If you want to write columns you make an array containing one array of all values.
The items you receive from the sheet are immutable and that's why you can't append to them, however you can copy the values into a new array and overwrite the old one. I however, would have taken another approach to this issue and just printed to the end of the column like this:
function appendToSheet() {
var sheet = SpreadsheetApp.getActive().getSheetByName('test'); // Get sheet so I don't have to retype it every time
var toAppend = [['Append 1'],['Append 2']]; // Note that this is an array of arrays.
var newRow = sheet.getLastRow() + 1; // This fetches the number of the last row of the entire sheet and adds one to it.
var endRange = lastRow + toAppend.length - 1; // Calculate the last row to append to
sheet.getRange('A' + newRow + ':A' + endRange).setValues(toAppend); // Write to sheet.
}
But if you want to use the sheet array and the appended data in your code elsewhere I'd do like this where I dynamically calculate the range I need and only fetch that, instead of fetching the entire sheet and work with that:
function appendToValues() {
var sheet = SpreadsheetApp.getActive().getSheetByName('test');
var lastRow = sheet.getLastRow();
var valuesFromSheet = sheet.getRange('A1:A' + lastRow).getValues(); // Get values from the sheet
var toAppend = [['value 1'],['value 2']];
var newArray = valuesFromSheet.concat(toAppend); // .concat() copies the old immutable array and makes a new one with the append array included.
}

Google Script - how to replace cell values in Sheet 1 by searching Sheet 2 for those values and returning correlating data from another Sheet 2 column

Google Spreadsheet / Scripting Question:
Disclaimer: I am a beginner. Any explanation helps me tremendously.
Long story short:
Worksheet 1, Column N contains comma-separated values.
Worksheet 2, Column A has all possible values that could be combined to make up the content of Worksheet 1, Column N.
Worksheet 2, Column C contains "alternative" values.
I need a script that can replace all values in Worksheet 1, Column N with the "alternative" values from Worksheet 2, Column C. I need the final result to be the "alternative" values in a single, comma-separated value.
I have already scripted to separate Column N values into individual values in new columns. However, I have not been able to advance further. My current splitting script appears at the bottom.
Full explanation:
"Worksheet 1" contains multiple columns, including Column "N" that contains comma-separated values. The number of rows in Sheet 1 will grow as users enter data. Currently, there are only three rows of data. Column "N" contains:
N1 has a value of "Dog, Cat, Rabbit"
N2 has a value of "Dog, Fish"
N3 has a value of "Frog, Horse, Fish"
My current Google Script gathers data from all available rows, and it then separates the comma-separated values in Column "N" into new columns, like so:
X1 has a value of "Dog", Y1 has a value of "Cat", and Z1 has a value "Rabbit"
X2 has a value of "Dog", Y2 has a value of "Fish"
X3 has a value of "Frog", Y3 has a value of "Horse", and Z3 has a value of "Fish"
"Worksheet 2" contains, in column A, all possible values that might appear above -- Dog, Cat, Rabbit, Fish, Horse, etc. So,
A1 has a value of "Dog"
A2 has a value of "Cat"
A3 has a value of "Rabbit"
A4 has a value of "Fish" -- etc. (there are 100+ total possible values).
"Worksheet 2" contains, in column C, "alternative values" (i.e., corresponding Google Calendar Resource Addresses):
C1 has a value of "domain.com_928313sdf98#resource.calendar.google.com"
C2 has a value of "domain.com_190382d0931#resource.calendar.google.com"
C3 has a value of "domain.com_295801a0181#resource.calendar.google.com"
C4 has a value of "domain.com_5s3910s1481#resource.calendar.google.com" --- etc.
I am seeking a script that, for the data in Worksheet 1, would search for the separated values in Worksheet 2 and then replace those values in Worksheet 1 with the correlating "alternative values" (i.e., Google Calendar Resource Addresses) from Worksheet 2, Column C. I then need it to concatenante the results back into a comma-separated value.
So, I want to start with Worksheet 1, where N1 has a value of "Dog, Cat, Rabbit," and I want to get back "domain.com_928313sdf98#resource.calendar.google.com, domain.com_190382d0931#resource.calendar.google.com, domain.com_295801a0181#resource.calendar.google.com" as my final result. The script would perform this across all rows.
My Splitting Script (I am not even sure if this is the best way of handling this):
function mySplit() {
var sh = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet();
var startcolumn = 2;
var startrow = 2;
var numcolumns = 500;
var dataRange = sh.getRange(startcolumn, 1, numcolumns, 25);
var data = dataRange.getValues();
for (var i = 0; i < data.length; ++i) {
var cell = sh.getRange(startcolumn + i, 15).getValues()[0];
var sCell = cell[0].split(",");
sh.getRange(startrow +i,26,1,sCell.length).setValues([sCell]);
}}
As I already mentioned in your other post, this is quite simple to do with arrays, here is a working example with your new data: see sheet here (read only, make a copy to test)
function replaceTagsWithRessource(){ // in this example sheet, the function will replace aa with 11, bb with 22 etc...
var sh1 = SpreadsheetApp.getActiveSpreadsheet().getSheetByName('sheet1');
var sh2 = SpreadsheetApp.getActiveSpreadsheet().getSheetByName('sheet2');
var sourceCol = sh1.getRange('N2:N').getValues();
Logger.log(sourceCol)
var targetRef = sh2.getDataRange().getValues();
Logger.log(targetRef)
var newColN = []
for(var s in sourceCol){
var caltoUse = sourceCol[s][0].split(',');
var calID = []
for(var n in caltoUse){
for(var r in targetRef){
if(caltoUse[n]==targetRef[r][0]){ calID.push(targetRef[r][2])} // get the cal ref in col 3
}
}
newColN.push([calID.toString()]);
Logger.log(newColN)
}
sh1.getRange('N2:N').setValues(newColN);// replace original values with new values (comma separated calendar IDs)
}

Cannot convert error when assigning array to a range

Below is my code and on the last line of code I get a "Cannot convert error". To clarify the line: sheet.getRange throws the error.
That is all the error says; nothing more, just "Cannot convert". Also, this is the full code, so there is nothing else.
function days(){
var table = new Array(7);
for ( var i = 0; i < 7 ; i ++){
table[i] = i+2;
}
var sheet = SpreadsheetApp.getActiveSpreadsheet().getSheetByName("Want");
sheet.getRange("B2:B9").setValues(table);
}
I don't know anything about Google Apps Scripting, but I managed to find this on Google.
It appears your table needs to be a 2-dimensional array.
Perhaps this can help?
(code is from the link above)
var myTable = [[1, 2, 3, 4],[5, 6, 7, 8]];
var sheet = SpreadsheetApp.getActiveSheet();
sheet.getRange(1,1,2,4).setValues(myTable);
SetValues() takes a 2 dimensions array as argument, TABLE is a 1 dimension array... this cannot work as it is... It's easy to change though, make table a 2D array of 7 elements.
like this : table[i] = [i+2];
btw, range ('B2:B9') is 8 cells high and you only give 7 values... there will be a problem there !
I figured out the problem to this question, so I will answer the question so that others may benefit. The problem here is that the .setValues method for a Range object must be given a two dimensional array [][]. So I created a 0 dimensional array inside of the other one so that i now had a two dimensional array.
var array = new Array(7);
for (var i = 0; i < 7; i++) {
array[i] = new Array(0);
}

Resources