我正在尝试使用Javascript的一些更高级的OO功能,遵循Doug Crawford的“超级构造函数”模式。但是,我不知道如何使用Javascript的本机类型系统从我的对象中设置和获取类型。这是我现在的方式:
function createBicycle(tires) {
var that = {};
that.tires = tires;
that.toString = function () {
return 'Bicycle with ' + tires + ' tires.';
}
}
如何设置或检索新对象的类型?如果有正确的方法,我不想创建type
属性。
typeof
或instanceof
运算符?答案 0 :(得分:15)
在收集两个操作数值之后,instanceof
运算符在内部使用抽象[[HasInstance]](V)
操作,该操作依赖于原型链。
您发布的模式仅包含扩充对象,并且根本不使用原型链。
如果你真的想使用instanceof
运算符,你可以将另一个Crockford的技术Prototypal Inheritance与超级构造函数结合起来,基本上可以从Bicycle.prototype
继承,即使它是一个空对象,也只是为了愚弄instanceof
:
// helper function
var createObject = function (o) {
function F() {}
F.prototype = o;
return new F();
};
function Bicycle(tires) {
var that = createObject(Bicycle.prototype); // inherit from Bicycle.prototype
that.tires = tires; // in this case an empty object
that.toString = function () {
return 'Bicycle with ' + that.tires + ' tires.';
};
return that;
}
var bicycle1 = Bicycle(2);
bicycle1 instanceof Bicycle; // true
更深入的文章:
答案 1 :(得分:3)
如果您这样声明Bicycle
,instanceof
将有效:
function Bicycle(tires) {
this.tires = tires;
this.toString = function () {
return 'Bicycle with ' + tires + ' tires.';
}
}
var b = new Bicycle(2);
console.log(b instanceof Bicycle);
答案 2 :(得分:2)
如果您使用的是构造函数,那么比instanceOf更好的解决方案就是:
Object.toType = function(obj) {
return ({}).toString.call(obj).match(/\s([a-z|A-Z]+)/)[1].toLowerCase();
}
toType({a: 4}); //"object"
toType([1, 2, 3]); //"array"
(function() {console.log(toType(arguments))})(); //arguments
toType(new ReferenceError); //"error"
toType(new Date); //"date"
toType(/a-z/); //"regexp"
toType(Math); //"math"
toType(JSON); //"json"
toType(new Number(4)); //"number"
toType(new String("abc")); //"string"
toType(new Boolean(true)); //"boolean"
toType(new CreateBicycle(2)); //"createbicycle"
解释为什么这是最好的方式,这取决于This帖子。
答案 3 :(得分:1)
仅在Firefox中,您可以使用__proto__
属性替换对象的原型。否则,您无法更改已创建的对象的类型,您必须使用new
关键字创建新对象。
答案 4 :(得分:0)
在我看来,在一个设计合理 类型heirarchy,你不需要知道 单个对象的类型。 但我似乎是少数人 那一点。
如果您必须有型号标识, 说清楚。
MyClass.prototype.type =“MyClass”;
至少可靠且便携 为你的对象。它也适用于 上下文。 DOM对象是另一个 问题,虽然你可以做的事情
让自己更轻松window.type =“window”;
等等。
我认为上面引用的是Douglas Crockford写的。