我正在尝试覆盖Object.prototype.toString
以添加其他类描述的功能。
这是初始代码:
(function(toString){
Object.prototype.toString = function(){
if(this instanceof TestClass)
{
return '[object TestClass]';
}
return toString.apply(this, arguments);
}
})(Object.prototype.toString);
function TestClass(){}
var instance_obj = new TestClass();
Object.prototype.toString.call(instance_obj);
当我在控制台中运行它时,我得到以下输出:
[object TestClass]
好消息是它不会彻底改变工作方式Object.prototype.toString
,因此对于另一种类型 [即不是 TestClass],事情会按预期工作,例如Object.prototype.toString.call(12)
将输出[object Number]
.
到目前为止,此实现没有问题。但是,我有以下代码的另一个实现:
(function(toString){
var fn_code_str = `return function(){
if(this instanceof TestClass)
{
return '[object TestClass]';
}
return toString.apply(this, arguments);
}`;
var pre_fn = new Function(fn_code_str);
Object.prototype.toString = pre_fn();
})(Object.prototype.toString);
function TestClass(){}
var instance_obj = new TestClass();
Object.prototype.toString.call(instance_obj);
有了这个,我得到了 TestClass 的正确输出,但是当我使用其他东西时,比如12
,我得到一个 RangeError:
VM527:5 Uncaught RangeError: Maximum call stack size exceeded
at Function.[Symbol.hasInstance] (<anonymous>)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:5:21)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
at Number.eval (eval at <anonymous> (getElements.html:19), <anonymous>:10:29)
这似乎是递归的问题toString.apply
。但是,我不知道为什么第二个实现是递归的,如果第一个没有?
注意:第二个实现的原因是if(this instanceof MyClassType){return '[object MyClassType]'}
从数组中的类名列表中为不同的类动态添加类型检查代码[即]。换句话说,我没有为我提出的每个新类修改代码,而是将类名附加到数组中,并且自动生成条件语句。