常见设计模式基础知识问答

一、问答

(一)、写出 构造函数模式、混合模式、模块模式、工厂模式、单例模式、发布订阅模式的范例。
//单例模式范例
var  Car = (function(){
    var instance;
    function init() {
        //私有的变量和函数
        var speed = 0;
        return {
            //定义公共的属性和方法
            getSpeed: function(){
                return speed;
            },
            setSpeed: function( s ){
               speed = s;
            }
        };
    }
    return {
        getInstance: function() {
            if (!instance) {
                instance = init();
            }
            return instance;
        }
    };
}());
var car = Car.getInstance();
var car2 = Car.getInstance();
car === car2;

1、工厂模式:

    //工厂模式 ---通过函数创造一个对象 将其return出来
    function createPeople(age,name,sex) {
        var o= new Object();
        o.age=age;
        o.name=name;
        o.sex=sex;
        return o;
    }
    var p1=createPeople(18,"zhangsan","M"),
            p2=createPeople(20,"lisi","F");
    console.log(p1,p2)

2、构造函数模式:

    function People(age,name) {
        this.age=age;
        this.name=name;
        this.sayName=function () {
            console.log("I am",this.name)
        }
    }

    var p1=new People("1","gouzao");

3、混合模式

    function People(name,age) {
        this.name=name;
        this.age=age;
    }
    People.prototype.sayAge=function () {
        console.log("my age is",this.age)

    };

    function Students(name,age,teacherName) {
        this.teacherName=teacherName;
        People.call(this,name,age);
    }

    Students.prototype=Object.create(People.prototype);
    Students.prototype.constructor=Students;
    Students.prototype.sayHi=function () {
        console.log("Hi! I am student and my name is"+this.name)
    };

    var student1= new Students("混合",11,"teache11"),
    student2= new Students("混合2",22,"teache22");

4、模块模式:

    var People=(function () {
        var name="laomingzi";
        return{
            changeName: function (newName) {
                name=newName;
            },
            sayName:function () {
                console.log(name)

            }
        }
    }());
    People.sayName();
    People.changeName("xinmingzi");
    People.sayName();
    
    // 常见形式

   var Car=(function () {
       var carName="奔驰";
       function sayCarName() {
           console.log(carName)
       }
       return{
          sayNameFunc:sayCarName
       }

   }());
    Car.sayNameFunc()

模块模式相对其他模式来说,安全性会有所提升,例如上面的例子,我们不能够在外面直接访问carName这个变量;
模块模式其实使得js具有一定的封装功能;

5、单例模式:

    var Singleton = (function () {
        var instantiated;
        function init() {
            /*这里定义单例代码*/
            return {
                publicMethod: function () {
                    console.log('hello world');
                },
                publicProperty: 'test'
            };
        }

        return {
            getInstance: function () {
                if (!instantiated) {
                    instantiated = init();
                }
                return instantiated;
            }
        };
    })();

    /*调用公有的方法来获取实例:*/
    Singleton.getInstance().publicMethod();

 // var danli=(function() {
//      var instant;
//      function init() {
//          return {
//              publicMethod: function(){
//                  console.log("我是单例模式")
//              },
//              publicOtherProto:"我是单例模式的OtherProto"
//          }
//      }
//      return{
//          getInstance:function () {
//              if (!instant){
//                  instant=init();
//              }
//              return instant;
//          }
//      }
//
//  }());
//  danli.getInstance().publicMethod();

再举个单例模式例子:

var SingletonTester = (function () {

    //参数:传递给单例的一个参数集合
    function Singleton(args) {

        //设置args变量为接收的参数或者为空(如果没有提供的话)
        var args = args || {};
        //设置name参数
        this.name = 'SingletonTester';
        //设置pointX的值
        this.pointX = args.pointX || 6; //从接收的参数里获取,或者设置为默认值
        //设置pointY的值
        this.pointY = args.pointY || 10;

    }

    //实例容器
    var instance;

    var _static = {
        name: 'SingletonTester',

        //获取实例的方法
        //返回Singleton的实例
        getInstance: function (args) {
            if (instance === undefined) {
                instance = new Singleton(args);
            }
            return instance;
        }
    };
    return _static;
})();

var singletonTest = SingletonTester.getInstance({ pointX: 5 });
console.log(singletonTest.pointX); // 输出 5

其实单例一般是用在系统间各种模式的通信协调上。

6、发布订阅模式

//无传参模式
  EventCenter=(function () {
      var events={};
      return{
          on:function (evt,handle) {
              events[evt]=events[evt]||[];
              events[evt].push(handle);
          },
          fire:function (evt) {
              if (!events[evt]){ console.log("未绑定此事件"); return}
              for(var i=0;i
(二)、使用发布订阅模式写一个事件管理器,可以实现如下方式调用
EventManager.on('text:change', function(val){
    console.log('text:change...  now val is ' + val);  
});
EventManager.fire('text:change', '饥人谷');
EventManager.off('text:change');
    EventManager=(function () {
      var events={};
      return{
          on:function (evt,handle) {
              events[evt]=events[evt]||[];
              events[evt].push(handle);  //{事件1:[函数1,函数2]}
          },
          fire:function (evt) {
              if (!events[evt]){ console.log("未绑定此事件"); return}
              for(var i=0;i

运行结果:

常见设计模式基础知识问答_第1张图片
Paste_Image.png

二、代码

(一)、写一个函数createTimer,用于创建计时器,创建的计时器可分别进行计时「新增」。

ps: 1. 计时器内部写法参考前面的任务中Runtime的写法; 2. 体会工厂模式的用法

function createTimer(){
    //todo..    
}

var timer1 = createTimer();
var timer2 = createTimer();
timer1.start();
for(var i=0;i<100;i++){
    console.log(i);
}
timer2.start();
for(var i=0;i<100;i++){
    console.log(i);
}
timer1.end();
timer2.end();
console.log(timer1.get());
console.log(timer2.get());

代码如下:




    
    Title






预览地址: http://book.jirengu.com/jirengu-inc/jrg-renwu5/%E6%9D%8E%E5%BD%A9/renwu40/renwu40-1.html

(二)、封装一个曝光加载组件,能实现如下方式调用
//$target 是 jquery 对象
// 当窗口滚动时,如果$target 出现在可见区域,执行回调函数里面的代码,且在回调函数内,$(this)代表$target
Expouse.bind($target, function(){
    console.log($(this));    // $target
});



    
    Title
    
    


  • i am target

预览地址: http://book.jirengu.com/jirengu-inc/jrg-renwu5/%E6%9D%8E%E5%BD%A9/renwu40/renwu40-2A.html

// 当窗口滚动时,如果$target 出现在可见区域,执行回调函数里面的代码,且在回调函数内,$(this)代表$target。 仅执行一次回调函数,下次$target 曝光不再执行
Expourse.one($target, function(){
    console.log($(this));    // $target
})



    
    Title
    
    


  • i am target

预览地址:http://book.jirengu.com/jirengu-inc/jrg-renwu5/%E6%9D%8E%E5%BD%A9/renwu40/renwu40-2B.html

(三)、封装一个 轮播插件,分别使用对象方式和 jquery插件方式来调用
// 要求:html 里有多个carousel,当调用时启动全部的 carousel

//方式1
//通过插件的方式启动所有轮播
$('.carousel').carousel();

//方式2
//通过创建对象的方式启动所有轮播
$('.carousel').each(function(){
    new Carousel($(this));
});

a、 插件方法:




    
    27-1无限轮播
    
    

预览地址: http://book.jirengu.com/jirengu-inc/jrg-renwu5/%E6%9D%8E%E5%BD%A9/renwu40/renwu40-3A%E6%8F%92%E4%BB%B6%E6%B3%95.html

b、创建对象方法:





    
    27-1无限轮播
    
    

预览地址:http://book.jirengu.com/jirengu-inc/jrg-renwu5/%E6%9D%8E%E5%BD%A9/renwu40/renwu40-3B%E6%9E%84%E9%80%A0%E5%87%BD%E6%95%B0%E6%B3%95.html

另:JavaScript模式相关书籍
1、JavaScript模式 https://book.douban.com/subject/11506062/
2、JavaScript设计模式 https://book.douban.com/subject/3329540/
3、JavaScript设计模式与开发实践 https://book.douban.com/subject/26382780/

**本文版权归本人即笔名:该账户已被查封 所有,如需转载请注明出处。谢谢! *

你可能感兴趣的:(常见设计模式基础知识问答)