JavaScript 在控制台中更改构造函数名称

Tot*_*Tot 3 javascript debugging constructor

使用构造函数工厂,我希望这些构造函数在控制台中具有不同的名称,在记录它们的实例时也是如此。

这是我的问题的一个简化示例:

// Constructor factory //
function type(name, prototype) {
    function Constructor() {}
    Constructor.name ; // "Constructor"
    // Constructor.name = name  won't work properly.
    Object.defineProperty(Constructor, 'name', { value:name }) ;
    Constructor.prototype = prototype ;

    window[name] = Constructor ;
    return Constructor ;
}

// Creating constructor and instance //
type('Cat', { name:"", paws:4 }) ;
var chat = new Cat ;

// Tests //
Cat.name ; // "Cat"    -> Correct name
Cat ; // Constructor() { ... }     -> Incorrect name
chat ; // Constructor {name:"", paws:4}     -> Incorrect name
Run Code Online (Sandbox Code Playgroud)

在这种情况下有什么办法可以显示正确的名称吗?

使用最新版本的 Chrome (67) 进行测试。在这种情况下,我不想使用该class功能。

T.J*_*der 5

您可能会想,具有计算属性解决方法的对象可以解决此问题,但它不适用于您描述的构造函数场景(至少目前,在 Chrome 或Firefox中 确实如此,现在,在至少 Firefox v66;在 Edge 中也是如此,令我惊讶的是,在 Node.js 中也如此,尽管 Node.js 和 Chrome 都使用 V8 [请参阅此评论]):

const dynamicName = "foo" + Math.floor(Math.random() * 1000);
const obj = {
  [dynamicName]: function() {
  }
};
const f = obj[dynamicName];
const inst = new f();
console.log(f.name);	// works
console.log(f);				// nope (on Chrome)
console.log(inst);		// nope (on Chrome)
Run Code Online (Sandbox Code Playgroud)
Look in the real console.
Run Code Online (Sandbox Code Playgroud)

不幸的是,尽管Function#name现在是函数的一个指定功能,正如您所发现的,这name并不总是 JavaScript 引擎内部在堆栈跟踪等中使用的功能(但是;希望随着name成熟,这种情况会发生变化;它只是在ES2015)。

如果您确实需要这样做,那么它是您可以生成和执行动态代码的极少数地方之一,例如new Function

var Constructor = new Function("return function " + name + "() { };")();
Run Code Online (Sandbox Code Playgroud)

这会执行以下操作,但动态地使用name而不是nameGoesHere

var Constructor = (function() {
    return function nameGoesHere() { };
})();
Run Code Online (Sandbox Code Playgroud)

new Function创建了我们立即执行的外部函数。

实例(在真实控制台中查看输出):

var Constructor = new Function("return function " + name + "() { };")();
Run Code Online (Sandbox Code Playgroud)

显然,这假设您没有name从不受信任的来源获取信息。