華為開發(fā)之ArkTS高性能編程實(shí)踐 2024-07-04 周四

簡(jiǎn)介

JS的性能沒法和C++比,有些編碼習(xí)慣會(huì)影響性能,優(yōu)先選擇高效的寫法。
參考文章

高效寫法

  • 變量默認(rèn)用const修飾,編譯不過了改成let
const index = 10000; // 該變量在后續(xù)過程中未發(fā)生改變,建議聲明成常量
  • 避免整形和浮點(diǎn)型混用。既然這樣,為什么不推出int和double關(guān)鍵字,非要弄個(gè)number?
let intNum = 1;
intNum = 1.1;  // 該變量在聲明時(shí)為整型數(shù)據(jù),建議后續(xù)不要賦值浮點(diǎn)型數(shù)據(jù)

let doubleNum = 1.1;
doubleNum = 1;  // 該變量在聲明時(shí)為浮點(diǎn)型數(shù)據(jù),建議后續(xù)不要賦值整型數(shù)據(jù)
  • 循環(huán)中常量提取,減少屬性訪問次數(shù)
class Time {
  static start: number = 0;
  static info: number[] = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
}

/// 不好的寫法
function getNum(num: number): number {
  let total: number = 348;
  for (let index: number = 0x8000; index > 0x8; index >>= 1) {
    // 此處會(huì)多次對(duì)Time的info及start進(jìn)行查找,并且每次查找出來的值是相同的
    total += ((Time.info[num - Time.start] & index) !== 0) ? 1 : 0;
  }
  return total;
}
class Time {
  static start: number = 0;
  static info: number[] = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
}

/// 好的寫法
function getNum(num: number): number {
  let total: number = 348;
  const info = Time.info[num - Time.start];  // 從循環(huán)中提取不變量
  for (let index: number = 0x8000; index > 0x8; index >>= 1) {
    if ((info & index) != 0) {
      total++;
    }
  }
  return total;
}
  • 使用參數(shù)傳遞函數(shù)外的變量
/// 使用閉包會(huì)造成額外的閉包創(chuàng)建和訪問開銷
let arr = [0, 1, 2];

function foo(): number {
  return arr[0] + arr[1];
}

foo();
/// 使用參數(shù)傳遞函數(shù)外的變量來替代使用閉包。
let arr = [0, 1, 2];

function foo(array: number[]): number {
  return array[0] + array[1];
}

foo(arr);
  • 避免使用可選參數(shù),用默認(rèn)參數(shù)替代
/// 函數(shù)的可選參數(shù)表示參數(shù)可能為undefined,在函數(shù)內(nèi)部使用該參數(shù)時(shí),需要進(jìn)行非空值的判斷,造成額外的開銷。
function add(left?: number, right?: number): number | undefined {
  if (left != undefined && right != undefined) {
    return left + right;
  }
  return undefined;
}
/// 使用默認(rèn)參數(shù),減少空判斷,提高性能
function add(left: number = 0, right: number = 0): number {
  return left + right;
}
  • 數(shù)值數(shù)組推薦使用TypedArray,既然這樣,推出number類型的意義在哪里?恢復(fù)int和double不是更好?
/// 純數(shù)字,用number性能低
const arr1 = new Array<number>([1, 2, 3]);
const arr2 = new Array<number>([4, 5, 6]);
let res = new Array<number>(3);
for (let i = 0; i < 3; i++) {
  res[i] = arr1[i] + arr2[i];
}
const typedArray1 = new Int8Array([1, 2, 3]);
const typedArray2 = new Int8Array([4, 5, 6]);
let res = new Int8Array(3);
for (let i = 0; i < 3; i++) {
  res[i] = typedArray1[i] + typedArray2[i];
}
  • 運(yùn)行時(shí)在分配超過1024大小的數(shù)組或者針對(duì)稀疏數(shù)組,會(huì)采用hash表的方式來存儲(chǔ)元素。在該模式下,相比于用偏移訪問數(shù)組元素速度較慢。在代碼開發(fā)時(shí),應(yīng)盡量避免數(shù)組變成稀疏數(shù)組。
// 直接分配100000大小的數(shù)組,運(yùn)行時(shí)會(huì)處理成用hash表來存儲(chǔ)元素
let count = 100000;
let result: number[] = new Array(count);

// 創(chuàng)建數(shù)組后,直接在9999處賦值,會(huì)變成稀疏數(shù)組
let result: number[] = new Array();
result[9999] = 0;
  • 避免使用聯(lián)合類型數(shù)組
let arrNum: number[] = [1, 1.1, 2];  // 數(shù)值數(shù)組中混合使用整型數(shù)據(jù)和浮點(diǎn)型數(shù)據(jù)

let arrUnion: (number | string)[] = [1, 'hello'];  // 聯(lián)合類型數(shù)組
/// 根據(jù)業(yè)務(wù)需要,將相同類型的數(shù)據(jù)放置在同一數(shù)組中
let arrInt: number[] = [1, 2, 3];
let arrDouble: number[] = [0.1, 0.2, 0.3];
let arrString: string[] = ['hello', 'world'];
  • 避免頻繁拋出異常
/// 創(chuàng)建異常時(shí)會(huì)構(gòu)造異常的棧幀,造成性能損耗。
function div(a: number, b: number): number {
  if (a <= 0 || b <= 0) {
    throw new Error('Invalid numbers.')
  }
  return a / b
}

function sum(num: number): number {
  let sum = 0
  try {
    for (let t = 1; t < 100; t++) {
      sum += div(t, num)
    }
  } catch (e) {
    console.log(e.message)
  }
  return sum
}
/// 用特殊值NaN替代異常,提高性能
function div(a: number, b: number): number {
  if (a <= 0 || b <= 0) {
    return NaN
  }
  return a / b
}

function sum(num: number): number {
  let sum = 0
  for (let t = 1; t < 100; t++) {
    if (t <= 0 || num <= 0) {
      console.log('Invalid numbers.')
    }
    sum += div(t, num)
  }
  return sum
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容