Javascript编程模式(JavaScript Programming Patterns)Part 2.(高级篇)

  1. 模块编程模式的启示(Revealing Module Pattern)
  2. 客户端对象(Custom Objects)
  3. 懒函数定义(Lazy Function Definition)

Christian 不喜欢module pattern,并对此编程模式进行了研究.在此基础上想出了一些新的东西他称之为 Revealing Module Pattern. 正如其名, 这种模式来源于Module Pattern, 但相比之下结构感更强且利于理解,尤其是在开发团队中将自己的代码移交给别人更容易上手.

首先,他还是一种基础的function定义与回调:

var anchorChange4 = function () {}();

 

其次,定义属性与方法时我们不用花太多的时间去在意 他们是否是 private 或者 public:

 // this will be a private property
    var config = {
        colors: [ "#F63", "#CC0", "#CFF" ]
    }
    // this will be a public method
    var init = function () {
        var self = this;
    }
    // assign reference to current object to "self"
    // get all links on the page
    var anchors = document.getElementsByTagName("a");
    var size = anchors.length;
    for (var i = 0; i < size; i++) {
        anchors[i].color = config.colors[i];
        anchors[i].onclick = function () {
            self.changeColor(this, this.color);
            // this is bound to the anchor object
            return false;
        };
    }
    // this will be a public method
    var changeColor = function (linkObj, newColor) {
        linkObj.style.backgroundColor = newColor;
    }

 

现在我们说一下核心部分.切换到 Module Pattern模式下, 你已经注意到了在结束时return 语句中包含public 属性和方法. 在 Revealing Module Pattern模式下, 你只需要放入共享的属性与方法即可:

 return {
     // declare which properties and methods are supposed to be public
     init: init,
    changeColor: changeColor
    } 

 

只有2个公共属性需要初始化一个是 init (负责编译前的准备工作) 和 changeColor (负责函数调用时的 clicked事件). 这样代码保持了整洁:

  // revealing module pattern
    var anchorChange4 = function () {
        // this will be a private property
        var config = { colors: [ "#F63", "#CC0", "#CFF" ] }
        // this will be a public method
        var init = function () {
            var self = this;
        }
        // assign reference to current object to "self"
        // get all links on the page
        var anchors = document.getElementsByTagName("a");
        var size = anchors.length;
        for (var i = 0; i < size; i++) {
            anchors[i].color = config.colors[i];
            anchors[i].onclick = function () {
                self.changeColor(this, this.color);
                // this is bound to the anchor object
                return false;
            };
        }


        // this will be a public method
        var changeColor = function (linkObj, newColor) {
            linkObj.style.backgroundColor = newColor;
        }

        return {
            // declare which properties and methods are supposed to be public
            init: init,
            changeColor: changeColor
        }
    } ();

 

与所有的编程模式一样, 你需要在script代码快中调用:

 <script type="text/javascript"> 
            anchorChange4.init(); 
 </script>

 

 

客户端对象(Custom Objects)

创建一类对象在面向对象的语言中很常见. 但是Javascript与面向对象相比较是基于对象的语言. 在JavaScript中, 在接受参数创建对象时你必须调用  function 构造器 .你不能像java 一样有类与子类( Java ).

首先, 我们需要为我们的对象创建函数构造器:

var anchorChanger = function () {};

 

我们初始化了一个空的函数构造器,稍后为对象添加 init 方法.

使用原型, 对我们的对象可以添加各种属性且可以访问. 最后设置了 3 属性, 也就是: config, changeColor and init.

    anchorChanger.prototype.config = {
        colors: [ "#F63", "#CC0", "#CFF" ]
    }

    anchorChanger.prototype.changeColor =
            function (linkObj, newColor) {
                linkObj.style.backgroundColor = newColor;
            };
    
    anchorChanger.prototype.init = function () {
        var self = this;
        var anchors = document.getElementsByTagName("a");
        var size = anchors.length;
        for (var i = 0; i < size; i++) {
            anchors[i].color = self.config.colors[i];
            anchors[i].onclick = function () {
                self.changeColor(this, this.color);
                return false;
            };
        }
    };

 

 Mike West指出, 使用原型的效率会很高.他不必每次都创建对象访问对象.

 

    // custom object constructor
    var anchorChanger = function () {
        this.init();
    };
    anchorChanger.prototype.config = {
        colors: [ "#F63", "#CC0", "#CFF" ]
    }
    anchorChanger.prototype.changeColor = function (linkObj, newColor) {
        linkObj.style.backgroundColor = newColor;
    };
    anchorChanger.prototype.init = function () {
        var self = this;
    } 
    // get all links on the page
    var anchors = document.getElementsByTagName("a");
    var size = anchors.length;
    for (var i = 0; i < size; i++) {
        anchors[i].color = self.config.colors[i];
        anchors[i].onclick = function () {
            self.changeColor(this, this.color);
            return false;
        };
    } ;

 

在页面中我们只需要声明一个 anchorChanger的接口即可:

<script type="text/javascript"> 
new anchorChanger(); 
</script>

 

惰性函数定义(Lazy Function Definition)

Peter Michaux 提出了 Lazy Function Definition 模式. 当你在页面中反复计算、调用函数多次时这种模式很实用.在这种模式下你要确定你的方法只做了一次,且仅仅做了一次.例子中 Peter 给出了在不同浏览器宿主环境不同而处理滚动的功能也不同.在不同浏览器模型中, 当函数在第一时间被调用时,滚动功能也不同(此处参看lazy-function-definition-pattern).

对于我们的任务而言,这种模式没有提供任何的优势,因为在这里我们没有繁重复杂的计算. 我们仅仅是展示一下这种模式是如何工作的:

var anchorChange5 = function () {};

 

像别的模式一样添加一些功能,代码如下:

  // define configuration
    var config = {
        colors: [ "#F63", "#CC0", "#CFF" ]
    };
    // get all links
    var anchors = document.getElementsByTagName("a");
    var size = anchors.length;
    // loop through anchors and attach events 
    for (var i = 0; i < size; i++) {
        anchors[i].color = config.colors[i];
        anchors[i].onclick = function ()
        { anchorChange5().changeColor(this, this.color); 
            return false;
        };
    } 

 

以上代码确保在调用时运行一次,所以不需要包含随后调用函数的性质.在 Lazy Function Definition 模式,需要从新定义函数声明:

  // redefine function so that it only holds the changeColor function 
    anchorChange5 = function () {
        return {
            changeColor: function (linkObj, newColor) {
                linkObj.style.backgroundColor = newColor;
            }
        };
    };

 

所以懒函数定义模式代码如下:

 // lazy function definition
    var anchorChange5 = function () {
        // define configuration 
        var config = { colors: [ "#F63", "#CC0", "#CFF" ] };
        // get all links
        var anchors = document.getElementsByTagName("a");
        var size = anchors.length;
        // loop through anchors and attach events
        for (var i = 0; i < size; i++) {
            anchors[i].color = config.colors[i];
            anchors[i].onclick = function () {
                anchorChange5().changeColor(this, this.color);
                return false;
            };
        }
        // redefine function so that it only holds the changeColor function
        anchorChange5 = function () {
            return { changeColor: function (linkObj, newColor) {
                linkObj.style.backgroundColor = newColor;
            } };
        };
    };

 

发生了什么:

  1. anchorChange5 在页面上调用和定义 config 变量与 anchors集合
  2. 每一个 anchor会被粘贴上一个onclick事件, 当被触发调用 changeColor方法并且从新声明 anchorChange5 function
  3. 在此之后, anchorChange5会从新声明并可以访问到只持有 changeColor 方法

在body之间,要调用 anchorChange5 :

<script type="text/javascript">    
            anchorChange5();
</script>

 

转载于:https://www.cnblogs.com/YcYYcY/p/3794005.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
With this digital Early Release edition of Programming JavaScript Applications, you get the entire book bundle in its earliest form—the author's raw and unedited content—so you can take advantage of this content long before the book's official release. You'll also receive updates when significant changes are made, as well as the final ebook version., Take your existing JavaScript skills to the next level and learn how to build complete web scale or enterprise applications that are easy to extend and maintain. By applying the design patterns outlined in this book, you’ll learn how to write flexible and resilient code that’s easier—not harder—to work with as your code base grows., JavaScript has become one of the most widely used—and essential—programming languages for the Web, on both the client-side and server-side. In the real world, JavaScript applications are fragile, and when you change them things often break. Author Eric Elliott shows you how to add features without creating bugs or negatively impacting the rest of your code during the course of building a large JavaScript application., Early Release content now available:, AMD, Asynchronous Operations, Callbacks, Promises and Deferreds, Code Quality, Function Polymorphism, Function Scope, Hoisting and Closures, Functional Programming and Stateless Functions, Immediately Invoked Function Expressions, Interfaces, JavaScript Style Guide, Lambdas, Method Chaining and Fluent APIs, Method Context, Named Parameters, Node Modules, Object Factories, Partial Application and Currying, Plugins, Principles of Modularity, Prototypal Inheritance, Prototype Cloning and the Flyweight Pattern, The Module Pattern, Unit Testing, Coming soon:, Architecting for Scale, Collaboration, Build, Continuous Integration, Deployment, Communicating with Servers and APIs, Designing and Programming RESTful APIs with Node.js, Event-driven, Modular Client Side Application Architecture, Feature Toggles, Internationalization, Logging and Cross Cu

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值