<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12
      代碼改變世界

      深入理解JavaScript系列(45):代碼復用模式(避免篇)

      2012-04-23 08:02  湯姆大叔  閱讀(16929)  評論(7)    收藏  舉報

      介紹

      任何編程都提出代碼復用,否則話每次開發一個新程序或者寫一個新功能都要全新編寫的話,那就歇菜了,但是代碼復用也是有好要壞,接下來的兩篇文章我們將針對代碼復用來進行討論,第一篇文避免篇,指的是要盡量避免使用這些模式,因為或多或少有帶來一些問題;第二排是推薦篇,指的是推薦大家使用的模式,一般不會有什么問題。

      模式1:默認模式

      代碼復用大家常用的默認模式,往往是有問題的,該模式使用Parent()的構造函數創建一個對象,并且將該對象賦值給Child()的原型。我們看一下代碼:

      function inherit(C, P) {
      C.prototype = new P();
      }

      // 父構造函數
      function Parent(name) {
      this.name = name || 'Adam';
      }
      // 給原型添加say功能
      Parent.prototype.say = function () {
      return this.name;
      };
      // Child構造函數為空
      function Child(name) {
      }

      // 執行繼承
      inherit(Child, Parent);

      var kid = new Child();
      console.log(kid.say()); // "Adam"

      var kiddo = new Child();
      kiddo.name = "Patrick";
      console.log(kiddo.say()); // "Patrick"

      // 缺點:不能讓參數傳進給Child構造函數
      var s = new Child('Seth');
      console.log(s.say()); // "Adam"

      這種模式的缺點是Child不能傳進參數,基本上也就廢了。

      模式2:借用構造函數

      該模式是Child借用Parent的構造函數進行apply,然后將child的this和參數傳遞給apply方法:

      // 父構造函數
      function Parent(name) {
      this.name = name || 'Adam';
      }

      // 給原型添加say功能
      Parent.prototype.say = function () {
      return this.name;
      };

      // Child構造函數
      function Child(name) {
      Parent.apply(this, arguments);
      }

      var kid = new Child("Patrick");
      console.log(kid.name); // "Patrick"

      // 缺點:沒有從構造函數上繼承say方法
      console.log(typeof kid.say); // "undefined"

      缺點也很明顯,say方法不可用,因為沒有繼承過來。

      模式3:借用構造函數并設置原型

      上述兩個模式都有自己的缺點,那如何把兩者的缺點去除呢,我們來嘗試一下:

      // 父構造函數
      function Parent(name) {
      this.name = name || 'Adam';
      }

      // 給原型添加say功能
      Parent.prototype.say = function () {
      return this.name;
      };

      // Child構造函數
      function Child(name) {
      Parent.apply(this, arguments);
      }

      Child.prototype = new Parent();

      var kid = new Child("Patrick");
      console.log(kid.name); // "Patrick"
      console.log(typeof kid.say); // function
      console.log(kid.say()); // Patrick
      console.dir(kid);
      delete kid.name;
      console.log(kid.say()); // "Adam"

      運行起來,一切正常,但是有沒有發現,Parent構造函數執行了兩次,所以說,雖然程序可用,但是效率很低。

      模式4:共享原型

      共享原型是指Child和Parent使用同樣的原型,代碼如下:

      function inherit(C, P) {
      C.prototype = P.prototype;
      }

      // 父構造函數
      function Parent(name) {
      this.name = name || 'Adam';
      }

      // 給原型添加say功能
      Parent.prototype.say = function () {
      return this.name;
      };

      // Child構造函數
      function Child(name) {
      }

      inherit(Child, Parent);

      var kid = new Child('Patrick');
      console.log(kid.name); // undefined
      console.log(typeof kid.say); // function
      kid.name = 'Patrick';
      console.log(kid.say()); // Patrick
      console.dir(kid);

      確定還是一樣,Child的參數沒有正確接收到。

      模式5:臨時構造函數

      首先借用構造函數,然后將Child的原型設置為該借用構造函數的實例,最后恢復Child原型的構造函數。代碼如下:

      /* 閉包 */
      var inherit = (function () {
      var F = function () {
      };
      return function (C, P) {
      F.prototype = P.prototype;
      C.prototype = new F();
      C.uber = P.prototype;
      C.prototype.constructor = C;
      }
      } ());

      function Parent(name) {
      this.name = name || 'Adam';
      }

      // 給原型添加say功能
      Parent.prototype.say = function () {
      return this.name;
      };

      // Child構造函數
      function Child(name) {
      }

      inherit(Child, Parent);

      var kid = new Child();
      console.log(kid.name); // undefined
      console.log(typeof kid.say); // function
      kid.name = 'Patrick';
      console.log(kid.say()); // Patrick
      var kid2 = new Child("Tom");
      console.log(kid.say());
      console.log(kid.constructor.name); // Child
      console.log(kid.constructor === Parent); // false

      問題照舊,Child不能正常接收參數。

      模式6:klass

      這個模式,先上代碼吧:

      var klass = function (Parent, props) {

      var Child, F, i;

      // 1.
      // 新構造函數
      Child = function () {
      if (Child.uber && Child.uber.hasOwnProperty("__construct")) {
      Child.uber.__construct.apply(this, arguments);
      }
      if (Child.prototype.hasOwnProperty("__construct")) {
      Child.prototype.__construct.apply(this, arguments);
      }
      };

      // 2.
      // 繼承
      Parent = Parent || Object;
      F = function () {
      };
      F.prototype = Parent.prototype;
      Child.prototype = new F();
      Child.uber = Parent.prototype;
      Child.prototype.constructor = Child;

      // 3.
      // 添加實現方法
      for (i in props) {
      if (props.hasOwnProperty(i)) {
      Child.prototype[i] = props[i];
      }
      }

      // return the "class"
      return Child;
      };

      var Man = klass(null, {
      __construct: function (what) {
      console.log("Man's constructor");
      this.name = what;
      },
      getName: function () {
      return this.name;
      }
      });

      var first = new Man('Adam'); // logs "Man's constructor"
      first.getName(); // "Adam"

      var SuperMan = klass(Man, {
      __construct: function (what) {
      console.log("SuperMan's constructor");
      },
      getName: function () {
      var name = SuperMan.uber.getName.call(this);
      return "I am " + name;
      }
      });

      var clark = new SuperMan('Clark Kent');
      clark.getName(); // "I am Clark Kent"

      console.log(clark instanceof Man); // true
      console.log(clark instanceof SuperMan); // true

      怎么樣?看著是不是有點暈,說好點,該模式的語法和規范擰得和別的語言一樣,你愿意用么?咳。。。

      總結

      以上六個模式雖然在某種特殊情況下實現了某些功能,但是都存在各自的缺點,所以一般情況,大家要避免使用。

      參考:http://shichuan.github.com/javascript-patterns/#code-reuse-patterns

      同步與推薦

      本文已同步至目錄索引:深入理解JavaScript系列

      深入理解JavaScript系列文章,包括了原創,翻譯,轉載等各類型的文章,如果對你有用,請推薦支持一把,給大叔寫作的動力。

      主站蜘蛛池模板: 极品少妇无套内射视频| 特级做a爰片毛片免费看无码| 亚洲精品国模一区二区| 色先锋av影音先锋在线| 女人张开腿无遮无挡视频| 无码成a毛片免费| 亚洲大尺度无码专区尤物| 精品国产成人一区二区| 欧美一区二区三区欧美日韩亚洲 | 亚洲全网成人资源在线观看| 国产日产欧产精品精品| 潮州市| 亚洲国产激情一区二区三区| 亚洲综合在线日韩av| 成人午夜福利视频后入| 麻豆国产97在线 | 欧美| 91精品人妻中文字幕色| 久久亚洲精品中文字幕波多野结衣 | 熟女国产精品一区二区三| 中文字幕亚洲人妻一区| 美女黄18以下禁止观看| 色猫咪av在线观看| 中文字幕一区二区三区精彩视频| 特级毛片a片久久久久久| 日产精品久久久久久久 | 国产美女高潮流白浆视频| 国产自产视频一区二区三区| 日韩有码av中文字幕| 久久综合九色综合欧洲98| 成人精品日韩专区在线观看| 免费午夜无码片在线观看影院| 久久天天躁狠狠躁夜夜2020老熟妇| 日韩免费无码人妻波多野| 区一区二区三区中文字幕| 亚洲人成网站18禁止无码| 亚洲乱码一卡二卡卡3卡4卡| 色综合人人超人人超级国碰| 久久久久人妻精品一区三寸 | 国产超碰无码最新上传| 美日韩av一区二区三区| 亚洲成av人无码免费观看|