Reputation: 13
I'm new to Google Apps Script/Javascript and I'm in the midst of working on the second iteration of my original code in order to make it faster. My first code made a lot of gets and sets to the underlying Google Sheet, while now I'm trying to do everything in arrays before setting the revised values. The current block of code I'm stuck on is my attempt to run an indexOf while running a map function.
The below script is about to run through every row of an array full of timesheet data and make various amendments to the columns and calculate new column values.
var = amendedTimesheetData = timesheetdata.map(function(item){
item.splice(2, 0, item[0] + " " + item[1]);
item.splice(4, 0, item[0].slice(0, 2) + item[1].slice(0, 2) + date(item[3]));
item.splice(0, 2);
item.splice(3, 0, "Open");
item.splice(4, 0, accountingCode); //SEE ISSUE BELOW
return item
})
}
The accounting code variable relies on having performed a Javascript version of a vlookup based on a value in one of the array columns. The looked-up value exists in another array pulled from a different tab in the sheet. I know the code to perform the lookup looks like this:
var timeTrackingCode = item[6]; //this is the location in the mapped array of the value to be looked up
var timeTrackingCodeRow = codeMappingData.map(function(r){ return r[0]; }).indexOf(timeTrackingCode);
var accountingCode = codeMappingData[timeTrackingCodeRow][1]
The formula in the code above relies on the codeMappingData variable which was made earlier in the parent function before the map function started running.
var codeMappingSheet = ss.getSheetByName('CodeMapping');
var codeMappingRange = codeMappingSheet.getDataRange();
var codeMappingData = codeMappingRange.getValues();
The Question: How do I reference the codeMappingData array while in the map function?
Other options to get around this would be to run a For loop separate from the map, but while trying to learn all the possibilities I'm stuck on trying to understand how I could pass the variable through and achieve all of the column manipulations in as little code as possible. Any guidance on how I could achieve the variable pass through, or tips on how the code could be more efficient would all be very valuable. I've only copied a bit of the code, so it might lack context, but I think the question is clear.
Note that I've assumed that it would be ill-advised to establish the codeMappingData variable within the Map function because then every time it iterates through a row it would be performing a get from the sheet? If I'm incorrect in assuming this, then perhaps the simplest approach is to establish the variable within the map.
Thank you,
Upvotes: 1
Views: 833
Reputation: 50426
The inner or child scope always has access to variables in the outer or parent scope.
function outerFunction(){
const outerScopeVar = 5;
const arr = [1,2,3];
arr.map(num => {
console.info(`I have access to both inner and outer scope variable: ${num} and ${outerScopeVar}`);
})
}
outerFunction();
Upvotes: 1
Reputation: 9571
You can use the thisArg
parameter as described in the Array.prototype.map() documentation. Just add it after your closing curly bracket and refer to it as this
within your map function, not codeMappingData
.
var timeTrackingCodeRow = codeMappingData.map(function(r) {
Logger.log(this[0]); // logs the first element of codeMappingData
return r[0];
}, codeMappingData).indexOf(timeTrackingCode);
Upvotes: 0