深度解析node的EventEmitter

在使用EventEmitter的時(shí)候我們常用的方法主要有on萎坷、emit脂崔、once、off, 下面我們簡(jiǎn)單實(shí)現(xiàn)一下這些方法

  1. 在實(shí)現(xiàn)這些方法之前爪飘,我們必須有一個(gè)構(gòu)造函數(shù)义起,并且需要導(dǎo)出去
function EventEmitter(){
    //這里使用Object.create創(chuàng)建對(duì)象,有人會(huì)問為什么不直接 this._events = {};
    //如果this._events = {} 這種方式上面是會(huì)存在__proto__  而Object.create創(chuàng)建的是沒有的师崎,是一個(gè)比較干凈的對(duì)象
    this._events = Object.create(null);    
}

   //導(dǎo)出
module.exports = EventEmitter;
  1. on方法的實(shí)現(xiàn)
EventEmitter.prototype.on = function(eventName,callback){

    if(!this._events){   // 這里做判斷的原因是解決如果一個(gè)新的對(duì)象繼承了EventEmitter 但是沒有this._events 屬性
        this._events = Object.create(null)
    }

    if(eventName !== 'newListener'){
        if(this._events['newListener']){
            this._events['newListener'].forEach(fn=>fn(eventName))
        }
    }

    let arr = this._events[eventName] || (this._events[eventName] = []);
    arr.push(callback);
}
  1. emit方法的實(shí)現(xiàn)
EventEmitter.prototype.emit = function(eventName,...args){

    if(!this._events){
        this._events = Object.create(null)
    }

    if(this._events[eventName]){
        this._events[eventName].forEach(fn => {
            fn(...args);
        });
    }
}
  1. once方法的實(shí)現(xiàn)
EventEmitter.prototype.once = function(eventName,callback){
    const once = (...args)=>{
        callback(...args);
        this.off(eventName,once)
    }
    once.l = callback;
    this.on(eventName,once)
}
  1. off方法的實(shí)現(xiàn)
EventEmitter.prototype.off = function(eventName,fn){
    if(this._events[eventName]){
        this._events[eventName] = this._events[eventName].filter(item=>{
            //filter返回false就會(huì)被刪掉
            return item !== fn && item.l !== fn;
        })
    }
}
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末默终,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子犁罩,更是在濱河造成了極大的恐慌齐蔽,老刑警劉巖,帶你破解...
    沈念sama閱讀 212,816評(píng)論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件昼汗,死亡現(xiàn)場(chǎng)離奇詭異肴熏,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)顷窒,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,729評(píng)論 3 385
  • 文/潘曉璐 我一進(jìn)店門蛙吏,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人鞋吉,你說我怎么就攤上這事鸦做。” “怎么了谓着?”我有些...
    開封第一講書人閱讀 158,300評(píng)論 0 348
  • 文/不壞的土叔 我叫張陵泼诱,是天一觀的道長。 經(jīng)常有香客問我赊锚,道長治筒,這世上最難降的妖魔是什么屉栓? 我笑而不...
    開封第一講書人閱讀 56,780評(píng)論 1 285
  • 正文 為了忘掉前任,我火速辦了婚禮耸袜,結(jié)果婚禮上友多,老公的妹妹穿的比我還像新娘。我一直安慰自己堤框,他們只是感情好域滥,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,890評(píng)論 6 385
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著蜈抓,像睡著了一般启绰。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上沟使,一...
    開封第一講書人閱讀 50,084評(píng)論 1 291
  • 那天委可,我揣著相機(jī)與錄音,去河邊找鬼格带。 笑死撤缴,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的叽唱。 我是一名探鬼主播屈呕,決...
    沈念sama閱讀 39,151評(píng)論 3 410
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼棺亭!你這毒婦竟也來了虎眨?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,912評(píng)論 0 268
  • 序言:老撾萬榮一對(duì)情侶失蹤镶摘,失蹤者是張志新(化名)和其女友劉穎嗽桩,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體凄敢,經(jīng)...
    沈念sama閱讀 44,355評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡碌冶,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,666評(píng)論 2 327
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了涝缝。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片扑庞。...
    茶點(diǎn)故事閱讀 38,809評(píng)論 1 341
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖拒逮,靈堂內(nèi)的尸體忽然破棺而出罐氨,到底是詐尸還是另有隱情,我是刑警寧澤滩援,帶...
    沈念sama閱讀 34,504評(píng)論 4 334
  • 正文 年R本政府宣布栅隐,位于F島的核電站,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏租悄。R本人自食惡果不足惜谨究,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 40,150評(píng)論 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望恰矩。 院中可真熱鬧记盒,春花似錦憎蛤、人聲如沸外傅。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,882評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽萎胰。三九已至,卻和暖如春棚辽,著一層夾襖步出監(jiān)牢的瞬間技竟,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,121評(píng)論 1 267
  • 我被黑心中介騙來泰國打工屈藐, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留榔组,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 46,628評(píng)論 2 362
  • 正文 我出身青樓联逻,卻偏偏與公主長得像搓扯,于是被迫代替她去往敵國和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子包归,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,724評(píng)論 2 351

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