最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

JavaScript實(shí)現(xiàn)AOP詳解(面向切面編程,裝飾者模式)

 更新時(shí)間:2017年12月19日 09:50:34   作者:三十億少女的夢  
下面小編就為大家分享一篇JavaScript實(shí)現(xiàn)AOP的方法(面向切面編程,裝飾者模式),具有很好的參考價(jià)值,希望對大家有所幫助。一起跟隨小編過來看看吧

什么是AOP?

AOP(面向切面編程)的主要作用是把一些跟核心業(yè)務(wù)邏輯模塊無關(guān)的功能抽離出來,這些跟業(yè)務(wù)邏輯無關(guān)的功能通常包括日志統(tǒng)計(jì)、安全控制、異常處理等。把這些功能抽離出來之后, 再通過“動態(tài)織入”的方式摻入業(yè)務(wù)邏輯模塊中。

AOP能給我們帶來什么好處?

AOP的好處首先是可以保持業(yè)務(wù)邏輯模塊的純凈和高內(nèi)聚性,其次是可以很方便地復(fù)用日志統(tǒng)計(jì)等功能模塊。

JavaScript實(shí)現(xiàn)AOP的思路?

通常,在 JavaScript 中實(shí)現(xiàn) AOP,都是指把一個(gè)函數(shù)“動態(tài)織入”到另外一個(gè)函數(shù)之中,具體的實(shí)現(xiàn)技術(shù)有很多,下面我用擴(kuò)展 Function.prototype 來做到這一點(diǎn)。請看下面代碼:

Function.prototype.before = function (beforefn) {
  var _self = this; //保存原函數(shù)引用
  return function () { //返回包含了原函數(shù)和新函數(shù)的"代理函數(shù)"
   beforefn.apply(this, arguments); //執(zhí)行新函數(shù),修正this
   return _self.apply(this, arguments); //執(zhí)行原函數(shù)
  }
 };
 Function.prototype.after = function (afterfn) {
  var _self = this;
  return function () {
   var ret = _self.apply(this, arguments);
   afterfn.apply(this, arguments);
   return ret;
  }
 };
 var func = function () {
  console.log("2")
 }
 func = func.before(function () {
  console.log("1");
 }).after(function () {
  console.log("3");
 } )
 func();

執(zhí)行結(jié)果如下:

我把負(fù)責(zé)打印數(shù)字1和打印數(shù)字3的兩個(gè)函數(shù)通過AOP的方式動態(tài)植入func函數(shù)。通過執(zhí)行上面的代碼,我們看到控制臺順利地返回了執(zhí)行結(jié)果1、2、3。

這種使用AOP的方式來給函數(shù)添加職責(zé),也是JavaScript語言中的一種非常特別的巧妙的裝飾者模式實(shí)現(xiàn),下面我們來試試Function.prototype.before的威力,請看下面代碼:

Function.prototype.before = function (beforefn) {
  var __self = this; // 保存原函數(shù)的引用
  return function () { // 返回包含了原函數(shù)和新函數(shù)的"代理"函數(shù)
   beforefn.apply(this, arguments); // 執(zhí)行新函數(shù),且保證 this 不被劫持,新函數(shù)接受的參數(shù) // 也會被原封不動地傳入原函數(shù),新函數(shù)在原函數(shù)之前執(zhí)行
   return __self.apply(this, arguments); // 執(zhí)行原函數(shù)并返回原函數(shù)的執(zhí)行結(jié)果, 2 // 并且保證 this 不被劫持
  }
 }
 Function.prototype.after = function (afterfn) {
  var __self = this;
  return function () {
   var ret = __self.apply(this, arguments);
   afterfn.apply(this, arguments);
   return ret;
  }
 };
 document.getElementById = document.getElementById.before(function(){ alert (1);
 });
 var button = document.getElementById( 'button' );

執(zhí)行結(jié)果:

我們給document.getElementById()做了一些裝飾,以后我們每次調(diào)用這個(gè)方法之前都會先執(zhí)行alert("1")這條語句,但是請注意我們這條語句并不是寫在了document.getElementById()這個(gè)方法的源碼中,而只是在他的外部給他加了裝飾,這樣帶來好處就是我們可以在不改變原方法的源碼的情況下為他添加一些新的行為。國際慣例,舉個(gè)栗子:

我的同事寫了一個(gè)函數(shù)可以輸出當(dāng)前時(shí)間,而我現(xiàn)在的需求是輸出當(dāng)前天氣之后再輸出當(dāng)前時(shí)間,下面有兩種解決思路:

(1)傳統(tǒng)解決辦法: 拿同事的函數(shù)過來,找到他輸出時(shí)間的代碼,在這些代碼之前加入輸出當(dāng)前天氣的代碼

(2)裝飾者模式解決辦法:拿同事的函數(shù)過來,不用看他的源碼,直接給他的函數(shù)裝飾一下,裝飾的東西也就是輸出當(dāng)前天氣的代碼。

兩種方法都解決了問題,但是他們的出發(fā)點(diǎn)是完全不同的:

(1)方法是改造原函數(shù)的內(nèi)部,我們就需要去理解源代碼,然后做修改。

(2)方法是給原函數(shù)添加了一層外套,我們根本不用管原本函數(shù)的內(nèi)部實(shí)現(xiàn)。

現(xiàn)在又有了新的需求:在輸出當(dāng)前時(shí)間之前,先輸出當(dāng)前溫度

(1)方法,我們在第一個(gè)需求已經(jīng)把同事的代碼改的面目全非了,現(xiàn)在又要重新理解函數(shù)內(nèi)部,并加以修改(刪除輸出當(dāng)前天氣的代碼,然后加入輸出當(dāng)前溫度的代碼)。

(2)方法,同事原本的函數(shù)是沒有變的,我們現(xiàn)在給同事的函數(shù)換一件套(輸出當(dāng)前溫度)就可以了。

以上這篇JavaScript實(shí)現(xiàn)AOP詳解(面向切面編程,裝飾者模式)就是小編分享給大家的全部內(nèi)容了,希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。

相關(guān)文章

  • 深入淺出es6模板字符串

    深入淺出es6模板字符串

    這篇文章主要介紹了深入淺出es6模板字符串,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2017-08-08
  • URL中“#” “?” &“”號的作用淺析

    URL中“#” “?” &“”號的作用淺析

    這篇文章主要介紹了URL中“#” “?” &“”號的作用淺析,非常不錯,具有參考借鑒價(jià)值,需要的朋友可以參考下
    2017-02-02
  • JS圖片無縫、平滑滾動代碼

    JS圖片無縫、平滑滾動代碼

    這篇文章主要介紹了JS圖片無縫、平滑滾動的實(shí)現(xiàn),需要的朋友可以參考下
    2014-03-03
  • 給easyui datebox擴(kuò)展一個(gè)清空的實(shí)例

    給easyui datebox擴(kuò)展一個(gè)清空的實(shí)例

    下面小編就為大家?guī)硪黄oeasyui datebox擴(kuò)展一個(gè)清空按鈕的實(shí)例。小編覺得挺不錯的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2016-11-11
  • JavaScript制作樓層導(dǎo)航效果流程詳解

    JavaScript制作樓層導(dǎo)航效果流程詳解

    項(xiàng)目中遇到比較多的的文檔內(nèi)容,為了方便查找里面的小內(nèi)容,一般都會在左側(cè)或者右側(cè)放一個(gè)固定樓層的導(dǎo)航欄,今天就來說一下這個(gè)固定樓層導(dǎo)航欄的思路以及實(shí)現(xiàn)的方法
    2021-10-10
  • 編寫兼容IE和FireFox的腳本

    編寫兼容IE和FireFox的腳本

    編寫兼容IE和FireFox的腳本確定的件很煩人的事,今日又經(jīng)歷了一次。
    2009-05-05
  • 基于gulp合并壓縮Seajs模塊的方式說明

    基于gulp合并壓縮Seajs模塊的方式說明

    本文介紹一個(gè)簡單可行的辦法,來做基于gulp構(gòu)建的中小型項(xiàng)目中的seajs合并壓縮,感興趣的朋友一起看看詳情吧
    2016-06-06
  • Bootstrap輸入框組件使用詳解

    Bootstrap輸入框組件使用詳解

    這篇文章主要為大家詳細(xì)介紹了Bootstrap輸入框組件的使用方法,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2017-06-06
  • JS數(shù)組方法reverse()用法實(shí)例分析

    JS數(shù)組方法reverse()用法實(shí)例分析

    這篇文章主要介紹了JS數(shù)組方法reverse()用法,結(jié)合實(shí)例形式分析了JS數(shù)組reverse()方法基本功能、用法與操作注意事項(xiàng),需要的朋友可以參考下
    2020-01-01
  • Js利用console計(jì)算代碼運(yùn)行時(shí)間的方法示例

    Js利用console計(jì)算代碼運(yùn)行時(shí)間的方法示例

    最近看了一本書,發(fā)現(xiàn)了個(gè)計(jì)算代碼執(zhí)行時(shí)間的方法,感覺還挺有用的,所以這篇文章主要給大家介紹了關(guān)于Javascript利用console計(jì)算代碼運(yùn)行時(shí)間的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),需要的朋友可以參考下。
    2017-09-09

最新評論

留坝县| 体育| 峨边| 肇东市| 华安县| 化州市| 富顺县| 濮阳县| 大冶市| 阜新市| 伊春市| 博爱县| 准格尔旗| 秦安县| 南开区| 洪雅县| 肥西县| 井研县| 南溪县| 衡山县| 梁河县| 武鸣县| 盐城市| 巴彦淖尔市| 肥西县| 永顺县| 宜昌市| 通河县| 开远市| 珲春市| 苍溪县| 惠水县| 双辽市| 吉林省| 科技| 泰和县| 斗六市| 东宁县| 龙游县| 郎溪县| 铜川市|