javascript - Är ett typescript-ellips ett prestandaproblem?
Typescript-ellipsis genererar JavaScript som konstruerar en array av arguments i början av funktionen.
function blah(...args: any[]){
}
blir :
function blah() {
var args = [];
for (var _i = 0; _i < (arguments.length - 0); _i++) {
args[_i] = arguments[_i + 0];
}
}
När jag ser över mitt projekt med prestanda i åtanke undrar jag om denna konstruktion är en prestandafråga för ofta anropad kod?
Är det?
Svar #1
Det enklaste sättet att svara på den frågan är att köra några tester. JsPerf är ett ganska fantastiskt verktyg för det. Jag var nyfiken själv så jag satte upp ett test här och ja, det kan vara en betydande prestandapåverkan. Hur mycket beror på hur ofta du anropar den funktionen, mängden arbete den gör och hur lång parameterlistan sannolikt kommer att bli.
Med allt det sagt är jag en stor anhängare av 80/20-regeln, särskilt när det gäller optimering. För det mesta spelar det ingen roll, så om det gör koden vackrare, kör på och använd det.
Svar #2
Jag håller med Jeffreys svar men jag tycker att en poäng har missats.
Du frågar om en restparameter orsakar en prestandaförlust, men jämfört med vad?
Till exempel, om jag hade följande funktion:
var addNums = function(...nums: number[]) {
var result = 0;
for (var i = 0; i < nums.length; i++) {
result += nums[i];
}
return result;
};
Vilka alternativ kan jag använda?
Om jag ville undvika restparametern skulle jag antagligen fortfarande acceptera ett arrayerargument med tanke på att vi inte vet hur många nummer det kan finnas. Körtidsprestandan skulle vara liknande i dessa två scenarier. Därför är restparametern bara en bekvämlighet för koden som anropar:
addNums(1,1,2,3);
Snarare än
addNums([1,1,2,3]);
Om TypeScript hade metodöverlagringar med sina egna funktionskroppar, skulle du kunna göra samma trick som har använts i C#-ramverksklassbiblioteket, där du tillhandahåller fasta metoder för en serie överlagringar och använder restparametern för att hantera fall med ett större antal argument - till exempel skulle du ha metodsignaturer såsom:
addNums(a: number, b: number)
addNums(a: number, b: number, c: number)
addNums(...nums: number[])
Så i de vanliga fallen skulle den icke-loopande versionen kallas, men i ytterliggare fall skulle den mindre effektiva versionen köras.
Du skulle kunna prova detta i TypeScript, men du skulle behöva tillhandahålla en enda kompatibel metodkropp för alla överlagringar och sedan kontrollera argumenten, vilket sannolikt inte kommer att vara snabbare (även om du skulle kunna mäta det).
Så om du inte tänker kalla denna metod tusen gånger, är det osannolikt att den är sämre än ett alternativ.
