JavaScript组合设计模式--改进引入案例分析


Posted in Javascript onMay 23, 2020

本文实例讲述了JavaScript组合设计模式--改进引入案例。分享给大家供大家参考,具体如下:

对于组合设计模式:

 (1)组合模式中把对象分为两种(组合对象,和叶子对象)
 (2)组合对象和叶子对象实现:同一批操作
 (3)对组合对象执行的操作可以向下传递到叶子节点进行操作
 (4)这样就会弱化类与类之间的耦合
 (5)他常用的手法是把对象组合成属性结构的对象

根据组合模式的这些特性我们改写代码如下:

由于用到了接口检验所以我们先引入接口文件代码

//定义一个静态方法来实现接口与实现类的直接检验
//静态方法不要写出Interface.prototype ,因为这是写到接口的原型链上的
//我们要把静态的函数直接写到类层次上
//定义一个接口类
var Interface=function (name,methods) {//name:接口名字
  if(arguments.length<2){
    alert("必须是两个参数")
  }
  this.name=name;
  this.methods=[];//定义一个空数组装载函数名
  for(var i=0;i<methods.length;i++){
    if(typeof methods[i]!="string"){
      alert("函数名必须是字符串类型");
    }else {
      this.methods.push( methods[i]);
    }
  }
};
Interface.ensureImplement=function (object) {
  if(arguments.length<2){
    throw new Error("参数必须不少于2个")
    return false;
  }
  for(var i=1;i<arguments.length;i++){
    var inter=arguments[i];
    //如果是接口就必须是Interface类型
    if(inter.constructor!=Interface){
      throw new Error("如果是接口类的话,就必须是Interface类型");
    }
    //判断接口中的方法是否全部实现
    //遍历函数集合
    for(var j=0;j<inter.methods.length;j++){
      var method=inter.methods[j];//接口中所有函数

      //object[method]传入的函数
      //最终是判断传入的函数是否与接口中所用函数匹配
      if(!object[method]||typeof object[method]!="function" ){//实现类中必须有方法名字与接口中所用方法名相同
        throw new Error("实现类中没有完全实现接口中的所有方法")
      }
    }
  }
}

(1)统一接口

var composite=new Interface("composite",["getChildByName","add"]);//侧重点获取子
var student=new Interface("composite",["goToClass","finishClass"]);//侧重点为每个对象的实现

(2)定义组合类

var compositeObj=function (name) {
         this.name=name;
         this.type="com";//默认是组合类
         var childs=new Array();
        //得到相关的所有孩子节点
         this.getChildByName=function (name) {
           //涉及到递归
           var toChilds=new Array();
           if(!name){
             for(var i=0;i<childs.length;i++){
                if(childs[i].type=="com"){
                  toChilds=toChilds.concat(childs[i].getChildByName())
                }else {
                  toChilds.push(childs[i]);
                }
             }
           }else {
             for (var i = 0; i < childs.length; i++){
               if(childs[i].name==name){
                 if(childs[i].type=="com"){
                   toChilds=toChilds.concat(childs[i].getChildByName());
                   break;
                 }else {
                   toChilds.push(childs[i]);
                   break;
                 }
               }else {
                 if(childs[i].type == "com"){
                   toChilds =toChilds.concat(childs[i].getChildByName(name));
                 }
               }
             }
               }
               return toChilds;
         };
         //增加子节点
         this.add=function (child) {
           childs.push(child);
           return this;
         };
         //去上课
        this.goToClass=function (name) {
        var toChilds=this.getChildByName(name);
         for(var i=0;i<toChilds.length;i++){
              toChilds[i].goToClass();
         }
      };
          //下课
         this.finishClass=function (name) {
      var toChilds=this.getChildByName(name);
      for(var i=0;i<toChilds.length;i++){
        toChilds[i].finishClass();
      }
    };
    Interface.ensureImplement(this,composite,student);
    };

(3)定义叶子类

var studentObj=function (name) {
    this.name=name;
    this.type="student";//默认是叶子
    //得到所有孩子节点
   this.getChildByName=function (name) {
     if(this.name==name){
       return this;
     }else {
       return null;
     }
   }
   //增加子节点
    this.add=function (child) {
      throw new Error("add 不成被初始化(在叶子了中)")
    }
    //去上课
    this.goToClass = function(name){
      document.write(this.name +" 去上课<br>");
    }
    //下课
    this.finishClass = function(name){
      document.write(this.name +" 下课<br>");
    }
    Interface.ensureImplement(this,composite,student);
  }

(4)应用---将学校,班级,组,学生关联起来

var astudent=new studentObj("我是a同学");
  var bstudent=new studentObj("我是b同学");
  var cstudent=new studentObj("我是c同学");
  var dstudent=new studentObj("我是d同学");
  var estudent=new studentObj("我是e同学");
  var fstudent=new studentObj("我是f同学");
  var gstudent=new studentObj("我是g同学");
  var hstudent=new studentObj("我是h同学");
  var istudent=new studentObj("我是i同学");

  var one = new compositeObj("一班");
  var oneOne = new compositeObj("一班一组");
  oneOne.add(astudent).add(bstudent);
  var oneTwo = new compositeObj("一班二组");
  oneTwo.add(cstudent).add(dstudent);

  one.add(oneOne).add(oneTwo);
  var two = new compositeObj("二班");
  var twoOne = new compositeObj("二班一组");
  twoOne.add(estudent).add(fstudent);
  var twoTwo = new compositeObj("二班二组");
  twoTwo.add(gstudent).add(hstudent).add(istudent)
  two.add(twoOne).add(twoTwo);
  var usPcat = new compositeObj("组合设计模式培训学校");
  usPcat.add(one).add(two);

(5)客户端调用API,只需要简单的安排去上课即可,也就是客户端只需要写去上课的代码即可

usPcat.goToClass();
document.write("-------------------------<br>");
usPcat.goToClass("一班");
document.write("-------------------------<br>");
usPcat.goToClass("二班一组");

感兴趣的朋友可以使用在线HTML/CSS/JavaScript代码运行工具:http://tools.3water.com/code/HtmlJsRun测试上述代码运行效果。

希望本文所述对大家JavaScript程序设计有所帮助。

Javascript 相关文章推荐
Javascript string 扩展库代码
Apr 09 Javascript
按给定几率进行随机抽取的js代码
Dec 28 Javascript
javascript实现可改变滚动方向的无缝滚动实例
Jun 17 Javascript
利用JS进行图片的切换即特效展示图片
Dec 03 Javascript
随鼠标上下滚动的jquery代码
Dec 05 Javascript
javascript实现可拖动变色并关闭层窗口实例
May 15 Javascript
JavaSciprt中处理字符串之sup()方法的使用教程
Jun 08 Javascript
Seajs是什么及sea.js 由来,特点以及优势
Oct 13 Javascript
vue-cli webpack 开发环境跨域详解
May 18 Javascript
Vue项目引发的「过滤器」使用教程
Mar 12 Javascript
layUI实现列表查询功能
Jul 27 Javascript
Vue CLI4 Vue.config.js标准配置(最全注释)
Jun 05 Javascript
JavaScript组合模式---引入案例分析
May 23 #Javascript
JavaScript设计模式--桥梁模式引入操作实例分析
May 23 #Javascript
JavaScript设计模式--简单工厂模式实例分析【XHR工厂案例】
May 23 #Javascript
JavaScript设计模式--简单工厂模式定义与应用案例详解
May 23 #Javascript
基于element-ui封装可搜索的懒加载tree组件的实现
May 22 #Javascript
微信小程序点击滚动到指定位置的实现
May 22 #Javascript
使用JavaScript通过前端发送电子邮件
May 22 #Javascript
You might like
PHP中的正则表达式函数介绍
2012/02/27 PHP
PhpMyAdmin出现export.php Missing parameter: what /export_type错误解决方法
2012/08/09 PHP
zf框架的校验器使用使用示例(自定义校验器和校验器链)
2014/03/13 PHP
PHP设计模式之迭代器模式
2016/06/17 PHP
Laravel中七个非常有用但很少人知道的Carbon方法
2017/09/21 PHP
PHP基于面向对象实现的留言本功能实例
2018/04/04 PHP
详解JavaScript中Hash Map映射结构的实现
2016/05/21 Javascript
细数JavaScript 一个等号,两个等号,三个等号的区别
2016/10/09 Javascript
详谈javascript精度问题与调整
2017/07/08 Javascript
vue修改vue项目运行端口号的方法
2017/08/04 Javascript
Node.Js生成比特币地址代码解析
2018/04/21 Javascript
详解vue组件中使用路由方法
2019/02/12 Javascript
Elementui表格组件+sortablejs实现行拖拽排序的示例代码
2019/08/28 Javascript
微信小程序关键字变色实现代码实例
2019/12/13 Javascript
Vue使用鼠标在Canvas上绘制矩形
2020/12/24 Vue.js
[20:39]DOTA2-DPC中国联赛 正赛开幕式 1月18日
2021/03/11 DOTA
合并Excel工作薄中成绩表的VBA代码,非常适合教育一线的朋友
2009/04/09 Python
Python中用Ctrl+C终止多线程程序的问题解决
2013/03/30 Python
简述Python中的面向对象编程的概念
2015/04/27 Python
自己使用总结Python程序代码片段
2015/06/02 Python
浅谈python import引入不同路径下的模块
2017/07/11 Python
解决Python中list里的中文输出到html模板里的问题
2018/12/17 Python
Python交互式图形编程的实现
2019/07/25 Python
windows环境中利用celery实现简单任务队列过程解析
2019/11/29 Python
使用TensorFlow搭建一个全连接神经网络教程
2020/02/06 Python
暇步士官网:Hush Puppies
2016/09/22 全球购物
Columbia美国官网:美国著名的户外服装品牌
2016/11/24 全球购物
init进程的作用
2012/04/12 面试题
SOA面试题:如何在SOA中实现松耦合
2013/07/21 面试题
党的群众路线教育实践活动批评与自我批评
2014/02/16 职场文书
质监局领导班子对照检查材料思想汇报
2014/09/27 职场文书
2015年学生会个人工作总结
2015/04/09 职场文书
HR必备:超全面的薪酬待遇管理方案!
2019/07/12 职场文书
golang中实现给gif、png、jpeg图片添加文字水印
2021/04/26 Golang
MySQL优化及索引解析
2022/03/17 MySQL
2022年显卡天梯图(6月更新)
2022/06/17 数码科技