I'm looking for a way to improve performance of my code.
My function has to convert String date format : 20200208 to 08/02/2020.
function convertToDate(sheet,col){
var s = sheet;
var col = col;
var newVal = new Array();
var oldVal = s.getRange(2,col,s.getLastRow()-1).getDisplayValues();
for (var i =0;i<=oldVal.length-1;i++){
var val = oldVal[i].toString();
var annee = val.slice(0,4);
var mois = val.slice(4,6);
var jour = val.slice(6,8);
//Logger.log(" Day: " + jour + "\nMonth : "+mois + "\nYear: "+annee);
var update = Utilities.formatDate(new Date(annee,mois-1,jour),Session.getScriptTimeZone(),"dd/MM/yyyy");
newVal.push(update);
//Logger.log(newVal[i])
}
for (var j = 2; j<= s.getLastRow();j++){
s.getRange(j,col).setValue(newVal[j-2]);
}
return Logger.log("end");
I've already read the Best Practises here : https://developers.google.com/apps-script/guides/support/best-practices
But I don't know how to applicate theses means in my function.
If sombody is able to correct me on some points, it could be very usefull !
Sincerely,
BigBenne
Your script is running slowly because use are writing cells one at a time. Use setValues() instead of setValue() to write them all at once. Try this:
function convertToDate(sheet, column) {
const firstRow = 2;
const range = sheet.getRange(firstRow, column, sheet.getLastRow() - firstRow + 1, 1);
const dateFormat = 'dd/MM/yyyy';
const timezone = sheet.getParent().getSpreadsheetTimeZone();
const newValues = range
.getDisplayValues()
.map(row => row.map(string => {
const annee = string.slice(0, 4);
const mois = string.slice(4, 6);
const jour = string.slice(6, 8);
return Utilities.formatDate(new Date(annee, mois - 1, jour), timezone, dateFormat);
}));
range.setValues(newValues);
}
Note that this function will not actually convert the values to dates but to text strings that look like dates. To get real numeric dates, use return new Date(annee, mois - 1, jour); and format the results in the spreadsheet through Format > Number > Date or a custom number format of your choice.
See this answer for an explanation of how date and time values work in spreadsheets.
So I just found a more efficiency way to do what I wanted.
I just remove the second for loop, it was useless, so I
s.getRange(i-2,col).setValue(newVal[i]); into the first for loop.
I am writing a function that takes an array of objects and parses the data into a date range. Right now I have the following:
function(result) {
var dates = [];
var data = [];
for (var i = 0; i < result.length; i++) {
var story = result[i];
var date = new Date(parseInt(story['UpdatedAt'].replace("/Date(", "").replace(")/", ""), 10));
date.setHours(0);
date.setMinutes(0);
date.setSeconds(0);
var estimate = story['Estimate'];
if (estimate == null)
estimate = 0;
if (dates[date] == null) {
dates[date] = [date, 1, estimate];
data.push(dates[date]);
} else {
dates[date][1] += 1;
dates[date][2] += estimate;
data.push(dates[date]);
}
}
console.log(dates);
drawStoriesCompletedChart(data);
}
I have two arrays, one for dates and one for data. The result of this function is fed into the Google Charts API, which requires the data to be [[a,b,c], [a,b,c]]
The code above works thanks to the way Google Charts works, but I do know that since the data array is being pushed to every single loop iteration, there will be a bunch of duplicates without updated data.
What I want is take the data from each object and parse it so it is like the following:
[[Date, Total Stories, Total Estimate], [...]] and have nothing else in the object.
I'm trying to fill the HeatMap calendar (http://cal-heatmap.com/) with dynamic data. So I'm taking different dates from a file and converting them to miliseconds to create the key-value pair required for the calendar.
I'm doing this like this:
var aux = {};
var dataJSON = {};
for(var i=0; i<activity.length; i++) {
var date = new Date(activity[i].date); // Date of activity
var ms = date.getTime(); // Date Conversion
aux[ms] = 1; // Pair "Key-Value" for calendar data
dataJSON = JSON.stringify(aux); // Convert to JSON format
}
If I print the result of dataJSON, I get (apparently) the correct object:
{"1426204800000":1,"1426464000000":1,"1426636800000":1,"1426550400000":1,"1425945600000":1,"1426118400000":1,"1426032000000":1,"1432771200000":1,"1432857600000":1,"1432598400000":1,"1432684800000":1,"1432080000000":1,"1432166400000":1,"1425513600000":1,"1435708800000":1,"1439164800000":1,"1425427200000":1,"1432512000000":1,"1439251200000":1,"1425340800000":1,"1432252800000":1,"1439337600000":1,"1425254400000":1,"1425859200000":1,"1425686400000":1,"1435881600000":1,"1425600000000":1,"1435795200000":1,"1436400000000":1,"1436313600000":1,"1436227200000":1,"1436140800000":1,"1435536000000":1,"1434931200000":1,"1427673600000":1,"1434758400000":1,"1435276800000":1,"1427760000000":1,"1435190400000":1,"1435104000000":1,"1435017600000":1,"1427241600000":1,"1434672000000":1,"1427155200000":1,"1434585600000":1,"1427414400000":1,"1434499200000":1,"1427328000000":1,"1434412800000":1,"1433980800000":1,"1433894400000":1,"1434326400000":1,"1426809600000":1,"1427068800000":1,"1427846400000":1,"1434067200000":1,"1428451200000":1,"1438646400000":1,"1428364800000":1,"1438560000000":1,"1428278400000":1,"1438387200000":1,"1438905600000":1,"1438819200000":1,"1428537600000":1,"1438732800000":1,"1430092800000":1,"1430179200000":1,"1437177600000":1,"1437091200000":1,"1430265600000":1,"1429488000000":1,"1436486400000":1,"1429747200000":1,"1437004800000":1,"1429833600000":1,"1436918400000":1,"1429574400000":1,"1436832000000":1,"1429660800000":1,"1436745600000":1,"1429142400000":1,"1429228800000":1,"1428969600000":1,"1429056000000":1,"1435622400000":1,"1428883200000":1,"1428624000000":1,"1428710400000":1,"1430956800000":1,"1430870400000":1,"1430784000000":1,"1430697600000":1,"1431043200000":1,"1424736000000":1,"1424649600000":1,"1431907200000":1,"1424908800000":1,"1431648000000":1,"1424822400000":1,"1424995200000":1,"1431993600000":1,"1438300800000":1,"1431475200000":1,"1431561600000":1,"1431302400000":1,"1424476800000":1,"1431388800000":1,"1423958400000":1,"1438128000000":1,"1423872000000":1,"1438041600000":1,"1424131200000":1,"1424304000000":1,"1424217600000":1,"1430352000000":1,"1437609600000":1,"1437523200000":1,"1437436800000":1,"1437350400000":1,"1423180800000":1,"1433203200000":1,"1437955200000":1,"1433116800000":1,"1423612800000":1,"1423526400000":1,"1437696000000":1,"1433376000000":1,"1433289600000":1,"1438214400000":1,"1433808000000":1,"1433721600000":1};
However, I cannot see the result on the calendar. This is the calendar configuration:
var cal = new CalHeatMap();
cal.init({
itemSelector: "#cal-heatmap",
domain: "month",
subDomain: "x_day",
start: new Date(init),
data: dataJSON
});
Anyway, I tried it with these static data and, surprisingly, it works:
var dataJSON = {"1420498800":2,"1420585200":4,"1420671600":2,"1420758000":1,"1421103600":2,"1421190000":1,"1421276400":1,"1421362800":1,"1421622000":1,"1421708400":1,"1422226800":1,"1422313200":1,"1422399600":2,"1422486000":1,"1422572400":1,"1423695600":3,"1424127600":2,"1424214000":1,"1424300400":3,"1424386800":1,"1424646000":2,"1424732400":1,"1424818800":2,"1424905200":2,"1424991600":1,"1425337200":1,"1425855600":4,"1426201200":2,"1426460400":2,"1426546800":1,"1426633200":2,"1426719600":1,"1426806000":1,"1427065200":1,"1427151600":1,"1427238000":2,"1427324400":1,"1427670000":2,"1428361200":2,"1428447600":2,"1428534000":3,"1428620400":3,"1428966000":2,"1429138800":2,"1429225200":1,"1429484400":2,"1429570800":1,"1429657200":2,"1429743600":2,"1429830000":3};
On the other hand, I'm getting the following GET error from d3.js:
GET http://localhost:9000/%7B%221426204800000%22:2,%2...2,%221433808000000%22:2,%221433721600000%22:2%7D
Aborted
Hope you can tell me my mistake, thanks in advance.
The data conversion should be done through "afterLoadData(data)" function. So, in my example:
var parserData = function (data) {
var dataJSON = {};
for(var i=0; i<data.length; i++) {
var date = new Date(data[i].date); // Date of activity
var sec = date.getTime()/1000; // Convert to sec
// Pair "Key-Value" for calendar data
if(dataJSON[sec]) {
dataJSON[sec]++;
} else {
dataJSON[sec] = 1;
}
}
return dataJSON;
}
var cal = new CalHeatMap();
cal.init({
itemSelector: "#cal-heatmap",
domain: "month",
subDomain: "x_day",
data: activity_sorted_by_date, // Dates Array
afterLoadData: parserData // Parser function
});