摘要:最近在寫移動端的項目,目前還沒有引用任何庫,所以很多的方法都要自己寫。是沒有這個原生方法的,今日得閑,就自己實現一個吧。文檔中描述的原型是它的含義是將合并到中,并返回合并過的。
最近在寫移動端的項目,目前還沒有引用任何庫,所以很多的方法都要自己寫。
用慣了jQuery,當函數參數是對象的時候,定義默認參數的時候會寫一個defaultOptions對象,然后通過jQuery.extend將實參擴展到defaultOptions對象上。JavaScript是沒有extend這個原生方法的,今日得閑,就自己實現一個吧。
先想想這個函數需要做什么。jQuery extend文檔中描述的jQuery.extend原型是
jQuery.extend( target [, object1 ] [, objectN ] )
它的含義是將object1、object2...合并到target中,并返回合并過的target。這里面有兩個點需要注意一下。
合并是從后到前的;
target的值是被修改了的;
是深拷貝的(若是參數對象中有屬性是對象,也是會遞歸合并的);
其實若不想原始數據被更改也很簡單,只要第一個參數傳空對象就好了。
那,直接上代嗎吧:
void function(global){ var extend, _extend, _isObject; _isObject = function(o){ return Object.prototype.toString.call(o) === "[object Object]"; } _extend = function self(destination, source){ for (var property in source) { if (source.hasOwnProperty(property)) { // 若sourc[property]是對象,則遞歸 if (_isObject(source[property])) { // 若destination沒有property,賦值空對象 if (!destination.hasOwnProperty(property)) { destination[property] = {}; }; // 對destination[property]不是對象,賦值空對象 if (!_isObject(destination[property])) { destination[property] = {}; }; // 遞歸 self(destination[property], source[property]); } else { destination[property] = source[property]; }; } } } extend = function(){ var arr = arguments, result = {}, i; if (!arr.length) return {}; for (i = 0; i < arr.length; i++) { if (_isObject(arr[i])) { _extend(result, arr[i]) }; } arr[0] = result; return result; } global.extend = extend; }(window)
這樣似乎可以了。但是貌似有一個小問題,我們這里是按照參數順序從左到右依次執行的,但是其實若是最后一個參數有的屬性,前面的參數上的該屬性都不需要再擴展了。其實前面的所有參數都是將自己身上有的屬性而最后一個參數沒有的屬性補到最后一個參數上。既如此,是不是從參數列表的右側開始擴展更好一些。
修改以后的代碼:
void function(global){ var extend, _extend, _isObject; _isObject = function(o){ return Object.prototype.toString.call(o) === "[object Object]"; } _extend = function self(destination, source) { var property; for (property in destination) { if (destination.hasOwnProperty(property)) { // 若destination[property]和sourc[property]都是對象,則遞歸 if (_isObject(destination[property]) && _isObject(source[property])) { self(destination[property], source[property]); }; // 若sourc[property]已存在,則跳過 if (source.hasOwnProperty(property)) { continue; } else { source[property] = destination[property]; } } } } extend = function(){ var arr = arguments, result = {}, i; if (!arr.length) return {}; for (i = arr.length - 1; i >= 0; i--) { if (_isObject(arr[i])) { _extend(arr[i], result); }; } arr[0] = result; return result; } global.extend = extend; }(window)
寫代碼總是那么有意思!這里面可以看到,只要result身上有的屬性,都不需要再賦值了,嘿嘿。
當然,目前水平有限,這段代碼肯定也還有著優化空間,若看官有任何建議,還請不吝賜教。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/78045.html
摘要:不過的實現中,多了很多細節上的判斷,比如第一個參數是否是布爾值,是否是一個對象,不傳參數時的默認值等。 JavaScritp 專題系列第七篇,講解如何從零實現一個 jQuery 的 extend 函數 前言 jQuery 的 extend 是 jQuery 中應用非常多的一個函數,今天我們一邊看 jQuery 的 extend 的特性,一邊實現一個 extend! extend 基本用...
本篇內容主要就是元素選擇器功能用Javascript實現?! ∈紫日f下什么是元素選擇器? 想必大家對于jquery很了解,知道它有對元素的查找功能,解釋來說就是通過jquery的api獲取頁面元素的過程,該過程只需提供一個元素選擇的條件字符串即可獲取相應的滿足條件的頁面元素。元素選擇器即是指通過條件字符串獲取相應元素的一個工具函數。 元素選擇器分為id選擇器、class選擇器、標簽選擇器以...
摘要:任何函數都可以用做構造函數,構造函數必須使用運算符作為前綴來創建新的實例。當使用關鍵字來調用構造函數時,執行上下文從全局對象變成一個空的上下文,這個上下文代表了新生成的實例。默認情況下,如果構造函數中沒有返回任何內容,就會返回當前的上下文。 公開記錄學習JS MVC,不知道能堅持多久= =。以《基于MVC的JavaScript web富應用開發》為主要學習資料。 JavaScr...
摘要:我們已經回答了的構造函數和原型都是誰的問題,現在牽扯出來一個,我們繼續檢查的構造函數是全局對象上屬性叫的對象的原型是個匿名函數,按照關于構造函數的約定,它應該是構造函數的屬性我們給這個對象起個名字,叫。 我不確定JavaScript語言是否應該被稱為Object-Oriented,因為Object Oriented是一組語言特性、編程模式、和設計與工程方法的籠統稱謂,沒有一個詳盡和大家...
摘要:專題系列共計篇,主要研究日常開發中一些功能點的實現,比如防抖節流去重類型判斷拷貝最值扁平柯里遞歸亂序排序等,特點是研究專題之函數組合專題系列第十六篇,講解函數組合,并且使用柯里化和函數組合實現模式需求我們需要寫一個函數,輸入,返回。 JavaScript 專題之從零實現 jQuery 的 extend JavaScritp 專題系列第七篇,講解如何從零實現一個 jQuery 的 ext...
閱讀 2045·2023-04-26 02:23
閱讀 1789·2021-09-03 10:30
閱讀 1351·2019-08-30 15:43
閱讀 1191·2019-08-29 16:29
閱讀 530·2019-08-29 12:28
閱讀 2332·2019-08-26 12:13
閱讀 2169·2019-08-26 12:01
閱讀 2400·2019-08-26 11:56