Js 常用方法及問題匯總

數(shù)組扁平化

  • 常規(guī)方法:
    var arr = [1,[2,3]]
    var arr2 = [1,2,[3,[4,5]]]
    arr.flat(1) // [1,2,3]
    arr2.flat(2) // [1,2,3,4,5]
    
  • 騷方法:
    arr1.toString().split()
    arr2.toString().split(',')
    或者
    arr1.join(',').split(',')
    

類型判斷

  • typeof:
    typeof 1 // number
    tyupeof '' // string
    typeof Symbol() // symbol
    typeof undefined // undefined
    typeof Object // function
    typeof null // object ---shit!
    typeof [] // object
    typeof new Date() // object
    

可以看出typeof只能簡(jiǎn)單的判斷出基本類型秧秉,并且null還有坑

  • instanceof

    a instanceof b, 
    原理是a.__proto__...__proto__ 與 b.prototype 比較是否相等秘车,通俗的來講就是能否通過a的原型鏈找到b的原型婆瓜。(由此就會(huì)造成誤解 [] instanceof Object // true)
    
  • Object.prototype.toString.call()

    幾乎完美的判斷出類型
    Object.prototype.toString.call(1) // [object Number]
    Object.prototype.toString.call('') // [object String]
    Object.prototype.toString.call(null) // [object Null]
    ...
    

    但是據(jù)說ie6下有問題, string,null,undefined會(huì)誤判斷為object(未考證郊丛!)

遞歸爆棧問題

function f(n) {
  if (n === 0 || n === 1) return n 
  else return f(n - 1) + f(n - 2)
}
當(dāng)n過大時(shí),會(huì)報(bào)錯(cuò)超棺!

有以下幾種解決方案:

  • 改循環(huán)
    function fLoop(n, a = 0, b = 1) {  
      while (n--) {
        [a, b] = [b, a + b]
      }
      return a
    }
    
    
    • 尾遞歸優(yōu)化
     function f(n, a=0, b=1) {
        if (n === 0) return a
        return f(n--, b, a+b)
     }
    

如何限制某個(gè)function 只能通過new 調(diào)用着降?

function Fn(){
        if (!(this instanceof Fn)) {
                console.log('you cant call this function')
                return
        }
        console.log('congratulation!')
}
Fn() // you cant call this function
new Fn() // congratulation

Fn() 直接調(diào)用時(shí) this 指向 window, new 調(diào)用時(shí)將this與構(gòu)造器綁定了技矮,詳情見new 的模擬實(shí)現(xiàn)化漆。

mergeOptions

合并兩個(gè)對(duì)象估脆,生成一個(gè)新對(duì)象。(合并策略為后一個(gè)覆蓋前一個(gè))

const strategy = function (parent, child) {
    return child === undefined
            ? parent
            : child
}
function mergeOption (parent, child) {
    let options = {}
    parent = parent || {}
    function mergeFileds(key) {
        options[key] = strategy(parent[key], child[key])
    }
    for (key in parent) {
        mergeFileds(key)
    }
    for (key in child) {
        if (!Object.prototype.hasOwnProperty.call(parent, key)) {
            mergeFileds(key)
        }
    }
    return options
}
let a = {
    key1: 1,
    key2: 2
}
let b = {
    key2: 22,
    key3: 3
}
mergeOption(a,b) // {key1: 1, key2: 22, key3: 3}

以上是淺拷貝获三,不能合并嵌套對(duì)象旁蔼。

let a = {
    key1: 1,
    key2: {
        key21: 21,
        key22: 22
    }
}
let b = {
    key3: 3,
    key2: {
        key22: 222,
        key23: 23
    }
}
mergeOption(a,b) // {key1:1,key2:{key22:222,key23:23},key3:3}

如何能支持嵌套對(duì)象的merge呢? 實(shí)際上只需要改一下strategy即可疙教。

let strategy = function (parent, child) {
    let typeName = function (val) {
        return Object.prototype.toString.call(val).slice(8, -1)
    }
    if (typeName(child) === "Object") {
        return mergeOption(parent, child)
    } else {
        return child === undefined
                ? parent
                : child
    }
}
let a = {
    key1: 1,
    key2: {
        key21: 21,
        key22: 22
    }
}
let b = {
    key1: {key11: 11},
    key3: 3,
    key2: {
        key22: 222,
        key23: 23
    }
}
mergeOption(a,b) // {key1:{key11: 11},key2:{key21: 21,key22:222,key23:23},key3:3}

判斷兩個(gè)對(duì)象相等

export function looseEqual (a: any, b: any): boolean {
  // 當(dāng) a === b 時(shí)棺聊,返回true
  if (a === b) return true
  // 否則進(jìn)入isObject判斷
  const isObjectA = isObject(a)
  const isObjectB = isObject(b)
  // 判斷是否都為Object類型
  if (isObjectA && isObjectB) {
    try {
      // 調(diào)用 Array.isArray() 方法,再次進(jìn)行判斷
      // isObject 不能區(qū)分是真數(shù)組還是對(duì)象(typeof)
      const isArrayA = Array.isArray(a)
      const isArrayB = Array.isArray(b)
      // 判斷是否都為數(shù)組
      if (isArrayA && isArrayB) {
        // 對(duì)比a贞谓、bs數(shù)組的長(zhǎng)度
        return a.length === b.length && a.every((e, i) => {
          // 調(diào)用 looseEqual 進(jìn)入遞歸
          return looseEqual(e, b[i])
        })
      } else if (!isArrayA && !isArrayB) {
        // 均不為數(shù)組限佩,獲取a、b對(duì)象的key集合
        const keysA = Object.keys(a)
        const keysB = Object.keys(b)
        // 對(duì)比a裸弦、b對(duì)象的key集合長(zhǎng)度
        return keysA.length === keysB.length && keysA.every(key => {
          //長(zhǎng)度相等祟同,則調(diào)用 looseEqual 進(jìn)入遞歸
          return looseEqual(a[key], b[key])
        })
      } else {
        // 如果a、b中一個(gè)是數(shù)組理疙,一個(gè)是對(duì)象晕城,直接返回 false
        /* istanbul ignore next */
        return false
      }
    } catch (e) {
      /* istanbul ignore next */
      return false
    }
  } else if (!isObjectA && !isObjectB) {
    return String(a) === String(b)
  } else {
    return false
  }
}

以上部分實(shí)現(xiàn)來自Vue源碼

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市窖贤,隨后出現(xiàn)的幾起案子砖顷,更是在濱河造成了極大的恐慌,老刑警劉巖赃梧,帶你破解...
    沈念sama閱讀 207,248評(píng)論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件滤蝠,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡授嘀,警方通過查閱死者的電腦和手機(jī)物咳,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,681評(píng)論 2 381
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來蹄皱,“玉大人览闰,你說我怎么就攤上這事∠镎郏” “怎么了焕济?”我有些...
    開封第一講書人閱讀 153,443評(píng)論 0 344
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)盔几。 經(jīng)常有香客問我晴弃,道長(zhǎng),這世上最難降的妖魔是什么逊拍? 我笑而不...
    開封第一講書人閱讀 55,475評(píng)論 1 279
  • 正文 為了忘掉前任上鞠,我火速辦了婚禮,結(jié)果婚禮上芯丧,老公的妹妹穿的比我還像新娘芍阎。我一直安慰自己,他們只是感情好缨恒,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,458評(píng)論 5 374
  • 文/花漫 我一把揭開白布谴咸。 她就那樣靜靜地躺著轮听,像睡著了一般。 火紅的嫁衣襯著肌膚如雪岭佳。 梳的紋絲不亂的頭發(fā)上血巍,一...
    開封第一講書人閱讀 49,185評(píng)論 1 284
  • 那天,我揣著相機(jī)與錄音珊随,去河邊找鬼述寡。 笑死,一個(gè)胖子當(dāng)著我的面吹牛叶洞,可吹牛的內(nèi)容都是我干的鲫凶。 我是一名探鬼主播,決...
    沈念sama閱讀 38,451評(píng)論 3 401
  • 文/蒼蘭香墨 我猛地睜開眼衩辟,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼螟炫!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起艺晴,我...
    開封第一講書人閱讀 37,112評(píng)論 0 261
  • 序言:老撾萬榮一對(duì)情侶失蹤不恭,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后财饥,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體换吧,經(jīng)...
    沈念sama閱讀 43,609評(píng)論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,083評(píng)論 2 325
  • 正文 我和宋清朗相戀三年钥星,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了沾瓦。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,163評(píng)論 1 334
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡谦炒,死狀恐怖贯莺,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情宁改,我是刑警寧澤缕探,帶...
    沈念sama閱讀 33,803評(píng)論 4 323
  • 正文 年R本政府宣布,位于F島的核電站还蹲,受9級(jí)特大地震影響爹耗,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜谜喊,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,357評(píng)論 3 307
  • 文/蒙蒙 一潭兽、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧斗遏,春花似錦山卦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,357評(píng)論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)枚碗。三九已至,卻和暖如春铸本,著一層夾襖步出監(jiān)牢的瞬間肮雨,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,590評(píng)論 1 261
  • 我被黑心中介騙來泰國(guó)打工归敬, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人鄙早。 一個(gè)月前我還...
    沈念sama閱讀 45,636評(píng)論 2 355
  • 正文 我出身青樓汪茧,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親限番。 傳聞我的和親對(duì)象是個(gè)殘疾皇子舱污,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,925評(píng)論 2 344

推薦閱讀更多精彩內(nèi)容