熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> Java編程 >> JSP教程 >> 正文

jQuery數據緩存功能的實現思路

2013-11-15 12:14:05  來源: JSP教程 

  前言
對於jQuery的數據緩存相信大家都不會陌生jQuery緩存系統不僅運用於DOM元素動畫事件等都有用到這個緩存系統所以在平時實際應用中 我們經常需要給元素緩存一些數據並且這些數據往往和DOM元素緊密相關由於DOM元素(節點)也是對象 所以我們可以直接擴展DOM元素的屬性但是如果給DOM元素添加自定義的屬性和過多的數據可能會引起內存洩漏所以應該要盡量避免這樣做 因此更好的解決方法是使用一種低耦合的方式讓DOM和緩存數據能夠聯系起來

另外對於jQuerydata和jQueryremoveData靜態方法以及基於這兩個方法的原型擴展方法的介紹和用法就不多說了可以查看官方API文檔

實現思路
jQuery提供了一套靈活和強大的緩存方法
)先在jQuery內部創建一個cache對象{} 來保存緩存數據 然後往需要進行緩存的DOM節點上擴展一個值為expando的屬性 這裡是”jQuery” + (new Date)getTime()expando的值等於”jQuery”+當前時間 元素本身具有這種屬性的可能性很少所以可以忽略沖突
)接著把每個節點的dom[expando]的值都設為一個自增的變量id保持全局唯一性 這個id的值就作為cache的key用來關聯DOM節點和數據也就是說cache[id]就取到了這個節點上的所有緩存即id就好比是打開一個房間(DOM節點)的鑰匙 而每個元素的所有緩存都被放到了一個map映射裡面這樣可以同時緩存多個數據
)所以cache對象結構應該像下面這樣

復制代碼 代碼如下:
var cache = {
"uuid": { // DOM節點緩存數據"uuid"相當於dom[expando]
"name": value
"name": value
}
"uuid": { // DOM節點緩存數據“uuid"相當於dom[expando]
"name": value
"name": value
}
//
};

  
每個uuid對應一個elem緩存數據每個緩存對象是可以由多個name/value(名值對)對組成的而value是可以是任何數據類型的

簡單模擬實現
根據以上思路就可以簡單實現下jQuerydata和jQueryremoveDate的功能了

復制代碼 代碼如下:
(function(window undefined) {
var cacheData = {} // 用來存儲數據的對象
win = window // 把window緩存給一個變量
uuid =
// 聲明隨機數(位)
// 注意+new Date()生成的隨機數是Number類型與一個空字符串連接後(或使用toString方法轉型後)變成字符串才可使用slice方法
expando = "cacheData" + (+new Date() + "")slice();
// (+new Date())toString()slice()等價於expando
// 寫入緩存
var data = function(elem name value) {
// 或使用原生方法驗證字符串ObjectprototypetoStringcall(elem) === "[object String]"
// 如果elem為字符串
if (typeof elem === "string") {
// 如果傳入name參數則為寫入緩存
if (name !== undefined) {
cacheData[elem] = name;
}
// 返回緩存數據
return cacheData[elem];
// 如果elem為DOM節點
} else if (typeof elem === "object") {
var id
thisCache;
// 如果elem不存在expando屬性則添加一個expando屬性(第一次給元素設置緩存)否則直接獲取已有的expando和id值
if (!elem[expando]) {
id = elem[expando] = ++uuid;
thisCache = cacheData[id] = {};
} else {
id = elem[expando];
thisCache = cacheData[id];
}
// 把一個隨機數作為當前緩存對象的一個屬性利用該隨機數就能找到該緩存對象
if (!thisCache[expando]) {
thisCache[expando] = {};
}
if (value !== undefined) {
// 將數據存到緩存對象中
thisCache[expando][name] = value;
}
// 返回DOM元素存儲的數據
return thisCache[expando][name];
}
};
// 刪除緩存
var removeData = function(elem name) {
// 如果elem為字符串則直接刪除該屬性值
if (typeof elem === "string") {
delete cacheData[elem];
// 如果key為DOM節點
} else if (typeof elem === "object") {
// 如果elem不存在expando屬性則終止執行不用刪除緩存
if (!elem[expando]) {
return;
}
// 檢測對象是否為空
var isEmptyObject = function(obj) {
var name;
for (name in obj) {
return false;
}
return true;
}
removeAttr = function() {
try {
// IE即標准浏覽器可以直接使用delete來刪除屬性
delete elem[expando];
} catch (e) {
// IE/IE使用removeAttribute方法來刪除屬性
elemremoveAttribute(expando);
}
}
id = elem[expando];
if (name) {
// 只刪除指定的數據
delete cacheData[id][expando][name];
// 如果是空對象id所對應的數據對象全部刪除
if (isEmptyObject(cacheData[id][expando])) {
delete cacheData[id];
removeAttr();
}
} else {
// 刪除DOM元素存到緩存中的所有數據
delete cacheData[id];
removeAttr();
}
}
};
// 把data和removeData掛在window全局對象下這樣在外部也能訪問到這兩個函數
winexpando = expando;
windata = data;
winremoveData = removeData;
})(window undefined);

  
例子
HTML結構

復制代碼 代碼如下:
<div id="demo" style="height: px; width: px; background: #ccc; color: #fff; margin: px; textalign: center; lineheight: px;">
demo
</div>

  
js代碼

復制代碼 代碼如下:
windowonload = function() {
// 測試
var demo = documentgetElementById("demo");
// 寫入緩存
data(demo "myName" "hcy");
consolelog(data(demo "myName")); // hcy
data(demo "myBlog" "
consolelog(data(demo "myBlog")); //
// 刪除DOM元素的某個緩存值
removeData(demo "myBlog");
consolelog(data(demo "myBlog")); // undefined
consolelog(data(demo "myName")); // hcy
consolelog(demo[expando]); //
// 刪除DOM元素
removeData(demo);
consolelog(demo[expando]); // undefined
};

  
firefox下例子結果截圖

對於上述例子實現jQuery的簡單緩存系統先給該DOM元素添加一個隨機生成的屬性expando這個屬性用來存放訪問緩存數據的id值就好比DOM元素都有一把開啟緩存保險箱的鑰匙只要有了鑰匙就可以隨時開啟緩存保險箱 將本來存放到DOM元素中的數據都轉到了緩存中而DOM元素本身只要存儲一個簡單的屬性就可以了這樣就可以將由DOM元素引起的內存洩漏(具體會發生什麼狀況不知道大家都這麼說~)的風險規避到最小

結語
糊裡糊塗地又到了最後有一些術語或解釋上可能存在偏差望各位童鞋指正和給出一些建議另外從理論上講 data和removeData方法可以用於任何對象的緩存 不過如果運用於本地對象或window對象 會存在內存洩露循環引用等問題(^_^從網上看到的) 所以一般還是用於DOM節點比較適合還可以結合事件動畫對DOM節點進行緩存數據的操作pscache真的很重要!需要慢慢體會~
因為分享所以簡單因為分享所以快樂 


From:http://tw.wingwit.com/Article/program/Java/JSP/201311/20545.html
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.