Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
JavaScript中接口模式的运行示例或工作演示_Javascript_Oop_Design Patterns_Interface - Fatal编程技术网

JavaScript中接口模式的运行示例或工作演示

JavaScript中接口模式的运行示例或工作演示,javascript,oop,design-patterns,interface,Javascript,Oop,Design Patterns,Interface,我正在阅读《pro javascript设计模式》一书,发现理解第2章中给出的“接口”模式没有什么困难,因为没有完整的代码示例演示此模式的使用 我正在寻找一些帮助,通过一些正在运行的代码来理解这种模式,例如JSFIDLE等 这一模式在第14-22页的书中有解释,我不理解的主要问题是“addForm”方法在哪里以及如何调用。或 如果有人能用一些测试数据和对象来完成ResultFormatter示例,这将对理解模式非常有帮助 “Pro Javascript设计模式”一书的代码可以从下载,这是第2章

我正在阅读《pro javascript设计模式》一书,发现理解第2章中给出的“接口”模式没有什么困难,因为没有完整的代码示例演示此模式的使用

我正在寻找一些帮助,通过一些正在运行的代码来理解这种模式,例如JSFIDLE等

这一模式在第14-22页的书中有解释,我不理解的主要问题是“addForm”方法在哪里以及如何调用。或 如果有人能用一些测试数据和对象来完成ResultFormatter示例,这将对理解模式非常有帮助

“Pro Javascript设计模式”一书的代码可以从下载,这是第2章


谢谢你的帮助

我见过以不同方式实现的模式,但想法很简单:

  • 您有一个类—您的接口—它只指定一些函数的名称。(您可能希望有一个名为Interface的类,您的实际接口实例化该类,这样您的接口就属于Interface类型)
  • 然后,您就有了实现此类接口的其他类。这意味着第二个类必须至少具有接口指定的所有函数
  • 最后,您在其他地方还有其他一些函数,它希望接收实现接口的对象。在您提到的示例代码中,这个函数是addForm,它需要一个实现“Composite”和“FormItem”接口的对象
  • 然后,此函数循环遍历它期望的接口的所有方法,并检查传入的对象是否也具有这些方法。如果在传递到函数中的对象中找不到其中一个接口的方法,它将确定该对象未实现该接口,并引发异常
  • 有些人可能会发现这种模式由于涉及的开销而不实用,但考虑到Javascript缺乏对接口的本机支持,这是一个不错的解决方案。有些人可能还会发现,在Javascript中为小项目使用接口是一种过分的做法

    示例

    var Interface = function(name, methods) {
        this.name = name;
        this.methods = [];
    
        if (methods.constructor == Array)
            this.methods = methods;
        else if (methods.constructor == String)
            this.methods[0] = methods;
        else
            throw new Error("Interface must define methods as a String or an Array of Strings");
    };
    
    var InterfaceHelper  = {
        ensureImplements : function(obj, interfaces) {
           // If interfaces is not an array, assume it's a function pointer
           var toImplement = interfaces.constructor == Array ? interfaces : [interfaces];
           var interface;
    
           // For every interface that obj must implement:
           for (var i = 0, len = toImplement.length; i < len; i++) {
              interface = toImplement[i];
    
              // Make sure it indeed is an interface
              if (interface.constructor != Interface)
                 throw new Error("Object trying to implement a non-interface. "
                 + interface.name + " is not an Interface.");
    
              // Make sure obj has all of the methods described in the interface
              for (var j = 0, interfaceLen = interface.methods.length; j < interfaceLen; j++)
                 if (!obj[interface.methods[j]])
                    throw new Error("Interface method not implemented. " 
                    + interface.name + " defines method " + interface.methods[j]);
           }
    
           return true;
        }
    };
    
    var Drawable = new Interface("Drawable", ["onDraw"]);
    
    var Surface = function() {
       this.implements = ["Drawable"];
    
       this.onDraw = function() {
          console.log("Surface Drawing");
       };
    };
    
    var myDrawableSurface = new Surface();
    
    // Returns true
    InterfaceHelper.ensureImplements(myDrawableSurface, Drawable);
    
    // Returns false (Error thrown)
    InterfaceHelper.ensureImplements(myDrawableSurface, Array);
    

    完成了书中的示例,以下是工作:

    var接口=函数(名称、方法){
    if(arguments.length!=2){
    抛出新错误(“接口构造函数使用“+arguments.length+”参数调用,但预期正好为2。”);
    }
    this.name=名称;
    this.methods=[];
    for(var i=0,len=methods.length;ix:'+x+',y:'+y);
    };
    Map.prototype.zoom=函数(x){
    警报(“缩放:”+x);
    }
    Map.prototype.draw=函数(){
    警惕(“抽签”);
    };
    var map=newmap();
    var DynamicMap=新接口('DynamicMap',['centerOnPoint','zoom','draw']);
    函数displayRoute(mapInstance){
    接口。确保实现(mapInstance、DynamicMap);
    mapInstance.centerOnPoint(12,34);
    mapInstance.zoom(5);
    maInstance.draw();
    }
    显示路线(地图);​
    
    ES6为该语言添加了语法上的糖分。下面是同一示例的ES6实现

    类接口{
    构造函数(名称、方法){
    if(arguments.length<2){
    抛出新错误('接口至少需要2个参数'+参数.length
    +“已传递参数”)
    }
    this.name=name
    this.methods=[]
    methods.forEach(method=>{
    if(typeof方法!=='string'){
    抛出新错误('接口要求所有方法名作为字符串传递'+
    方法+'是一种“+类型的方法)
    }
    this.methods.push(方法)
    },这个);
    }
    静态ensureImplements(对象){
    if(arguments.length<2){
    抛出新错误(“调用的函数接口.ensureImplements”+
    arguments.length+“参数,但至少应为2。”)
    }
    for(设i=1,len=arguments.length;ivar Interface = function(name, methods) {
        if (arguments.length != 2) {
            throw new Error("Interface constructor called with " + arguments.length + "arguments, but expected exactly 2.");
        }
    
        this.name = name;
        this.methods = [];
    
        for (var i = 0, len = methods.length; i < len; i++) {
            if (typeof methods[i] !== 'string') {
                throw new Error("Interface constructor expects method names to be " + "passed in as a string.");
            }
    
            this.methods.push(methods[i]);
        }
    };
    
    // Static class method.
    Interface.ensureImplements = function(object) {
        if (arguments.length < 2) {
            throw new Error("Function Interface.ensureImplements called with " + arguments.length + "arguments, but expected at least 2.");
        }
    
        for (var i = 1, len = arguments.length; i < len; i++) {
            var interface = arguments[i];
    
            if (interface.constructor !== Interface) {
                throw new Error("Function Interface.ensureImplements expects arguments" + "two and above to be instances of Interface.");
            }
    
            for (var j = 0, methodsLen = interface.methods.length; j < methodsLen; j++) {
                var method = interface.methods[j];
    
                if (!object[method] || typeof object[method] !== 'function') {
                    throw new Error("Function Interface.ensureImplements: object " + "does not implement the " + interface.name + " interface. Method " + method + " was not found.");
                }
            }
        }
    };
    
    function Map() {}
    
    Map.prototype.centerOnPoint = function(x,y) {
        alert('center=> x: ' + x + ', y: ' + y);
    };
    
    Map.prototype.zoom = function(x){
        alert('zoom : ' + x);
    }
    
    Map.prototype.draw = function(){
        alert('draw');
    };
    
    var map = new Map();
    var DynamicMap = new Interface('DynamicMap', ['centerOnPoint', 'zoom', 'draw']);
    
    function displayRoute(mapInstance) {
        Interface.ensureImplements(mapInstance, DynamicMap);
        mapInstance.centerOnPoint(12, 34);
        mapInstance.zoom(5);
        mapInstance.draw();
    }
    
    displayRoute(map);​