仅在参数类型检查时才实例化JavaScript构造函数

时间:2017-05-13 10:00:19

标签: javascript

假设我有以下构造函数

function Planet(solarSystem,habitable) {

    this.solarSystem = solarSystem;
    this.habitable = habitable;

}

我想创建一个这个构造函数的实例但是我输入了错误的参数类型(例如因为我有4个啤酒,我觉得编程):

let earth = new Planet(23, 'wooow');

问题:如何调整实例的创建,以便在遵守参数类型的情况下使用>实例已创建,否则不会向earth

分配任何内容

编辑:我忘了指定我期待Planet(String, boolean)参数类型

2 个答案:

答案 0 :(得分:1)

有一些解决方案可以做到:

  • 返回没有任何属性的对象

    function Planet(solarSystem,habitable) {
        if (typeof solarSystem != 'string' && typeof habitable != 'boolean') {
           return Object.create(null);
        }
        this.solarSystem = solarSystem;
        this.habitable = habitable;
    }
    
    var planetObj1 = new Planet('TEST', true);
    console.log('planetObj1 ' , planetObj1 , 'is instanceof Planet', planetObj1 instanceof Planet);
    var planetObj2 = new Planet(14, 'TEST');
    console.log('planetObj2 ', planetObj2, 'is instanceof Planet', planetObj2  instanceof Planet);

  • 如果要返回任何其他JavaScript类型,例如undefined,null。你可以创建一个原型来处理它

您可以创建原型来决定是否创建新的Obj

function Planet(solarSystem,habitable) {

        this.solarSystem = solarSystem;
        this.habitable = habitable;

    }

    Planet.CreatePlanet = function(solarSystem, habitable) { 
        if (typeof solarSystem != 'string' && typeof habitable != 'boolean') return null;
        return new Planet(solarSystem, habitable);
    }

    // then instead of new Planet():
    var obj = Planet.CreatePlanet(14, 'habitable');//return null
    console.log(obj);

答案 1 :(得分:0)

您可以使用Proxy对象拦截现有构造函数并应用验证逻辑:

function Planet(solarSystem,habitable) {
    this.solarSystem = solarSystem;
    this.habitable = habitable;
}

const validate = { // handler for Proxy
  construct: function(target, args) {
    let solarSystem, habitable;
    if (Array.isArray(args) && args.length === 2) {
      solarSystem = (typeof args[0] === 'string') ? args[0] : null;
      habitable = (typeof args[1] === 'boolean') ? args[1] : null;
      return ( solarSystem !== null && habitable !== null)
      	? { solarSystem, habitable} 
        : {}
    } else {
    	return {} // return an empty object in case of bad arguments
    }
  }
}

// new constructor, use it to create new planets
const validPlanet = new Proxy(Planet, validate); 
// usage: const a = new validPlanet(<string>, <boolean>)

// let's use initial buggy constructor:

const earth = new Planet('solar', true);
console.log('earth (Planet): ', earth);

const wrong = new Planet('solar', 15); // this uses the initial constructor, wrong value passes
console.log('wrong (Planet): ', wrong);

// now let's use proxied constrictor with validation

const pluto = new validPlanet('solar', false);
console.log('pluto (validPlanet): ', pluto);

const bad = new validPlanet('solar', 'hello');
console.log('bad (validPlanet): ', bad); // returns an empty object

如果您提供了错误的输入,则无法在此处返回“未定义”,因为Proxy.construct 必须返回一个对象。如果一个空对象没问题,那么这应该适合你。