-
設計模式
- 發(fā)布訂閱-觀察者
- 事件池 存放->按順序執(zhí)行
- 模塊模式
- 閉包
- 工廠模式
- 無法區(qū)分關系
- 構造函數(shù)模式
- 混合模式(工廠 模塊)
- 定制化
- 單例模式
- 有且只有一個
- 發(fā)布訂閱-觀察者
-
JQ的發(fā)布訂閱
-
pond1=
('.submit').click(function(){
pond1.add(func) //添加到事件池中的方法
$pond1.remove(func) //移除事件池中的方法
-
-
DOM0和DOM2
- 語法上的區(qū)別
- dom0 box.onclick=function(){}
- dom2 box.addEventListener('click',function(a,b,c){}) //a:事件名 click b:方法名 c:true-捕獲階段調用 false-冒泡階段調用
- 底層運行機制
- dom0 元素某個屬性綁定方法值 有效綁定的方法只有一個(后面替換之前的)
- dom2 基于事件池機制完成,每增加一個綁定的方法,都會往事件池中存放一個 當事件觸發(fā)會依次執(zhí)行事件池中的事件(類似發(fā)布訂閱模式 模擬事件池機制),可以給同一個元素的某個事件綁定多個不同的方法
- dom2中可以給一些特殊的事件類型綁定方法,這些類型dom0不支持綁定,DOMContentLoaded(dom結構加載完成 觸發(fā)執(zhí)行事件)、transitioned(css3 過渡動畫執(zhí)行完成觸發(fā))
-
(function(){}) dom2 可以綁定多個
- dom結構加載完成就執(zhí)行
- window.onload dom0 只能綁定一個 => dom2 window.addEventListener('onload',function(){})
- dom樹+所有相關資源均加載完畢才執(zhí)行
-
- dom2的事件池機制
- 基于addEventListener/attachEvent(IE6-8)向事件池追加方法、新版本瀏覽器會根據(jù)元素和事件類型對新增方法做重復校驗,但是IE6-8不可以
- removeEventListener/dttachEvent刪除事件 不能移除匿名函數(shù)
- 當事件行為觸發(fā),會把事件池中的方法按照增加的順序執(zhí)行,但IE6-8中執(zhí)行的順序是不固定的(亂序執(zhí)行) 捕獲 目標 冒泡
- 語法上的區(qū)別
事件池--數(shù)組塌陷
let _subscribe=(function(){
//發(fā)布訂閱類subscribe
class Sub(){
constructor(){
//創(chuàng)建事件池 存儲后期需要執(zhí)行的方法
this.$pond = [];
//向事件池中追加方法 func(需要追加的方法 判斷是否是方法 去重)
add(func){
/*some
arr.some(item=>{
return item>1
})
找true
是否存在滿足條件的 true 循環(huán)結束沒有 false 不檢測空數(shù)組,不改變原始數(shù)組)
every
找false
找到后終止并返回false 每個對象是否滿足條件
find
arr.find(item=>{
return item.flag
})
返回找到的滿足條件的第一項,停止循環(huán) 不改變原始數(shù)組 循環(huán)完畢沒找到返回undefined,不檢測空數(shù)組)
includes(arr.includes(1) true/false) filter(篩選 返回新數(shù)組,不改變舊的)
map(映射 返回新數(shù)組,不改變舊的)
*/
let flag = this.$pond.some(item=>{
return item===func
})
if(!flag){
this.$pond.push(func)
}
// !flag ? this.$pond.push(func) : null;
}
//移除事件池中的方法
remove(func){
//splice filter 淺拷貝 堆內存 引用類型
let $pond=this.$pond;
for(let i=0;i<$pond.length;i++){
let item=$pond[i];
if(item===func){
//移除 不改變方法順序(改變順序 刪除當前項 將最后一項添加到當前位置,然后刪除最后一位--性能優(yōu)化) splice(i,n)
$pond.splice(i,1); //導致數(shù)組塌陷-->假移除 賦值為null
$pond[i]=null//解決數(shù)組塌陷 偽刪除 保證索引
break;
//終止循環(huán) 區(qū)別return(終止當次循環(huán))
}
}
}
//通知事件池中的方法依次執(zhí)行
fire(...args){ //...擴展運算符 args 傳進來所有參數(shù)的數(shù)組(不確定參數(shù)有幾個)
let $pond=this.$pond
for(let i=0;i<$pond.length;i++){
let item=$pond[i]
if(typeOf item!=='function'){
$pond.splice(i,1); //再進行刪除
i--;
continue;//跳過循環(huán)體中剩下的語句
}
item.call(this,...args) //this指向當前實例 單獨傳參 在三個或以上參數(shù)時 call的性能略優(yōu)與apply --apply 數(shù)組傳參
}
}
}
}
return function subscribe(){ //暴露外界使用 做普通函數(shù)
return new Sub()
}
})();//閉包 防止污染 沖突
let s1 = _subscribe(); //創(chuàng)建實例 事件池
document.querySelector('.submit').onclick=function(event){
let evt=event?event:window.event; //cancelBubble 取消事件冒泡 stopPropagation 取消事件冒泡和下沉
s1.fire(evt) //執(zhí)行事件池中的方法執(zhí)行
}
s1.add(func)
s1.remove(func)
- B站學習偶然看到的 up主-光影嗶哩 珠峰培訓課程
- 之前的知識忘卻大部分了 有錯誤的地方歡迎大佬聯(lián)系我改正
- 好久不學習了~ 咸魚太久了啊