javascript ES6 动态类名

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/33605775/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-28 16:40:36  来源:igfitidea点击:

ES6 Dynamic class names

javascriptclassecmascript-6

提问by simon-p-r

I have been experimenting with ES6 classes and am wondering if you can change class names dynamically? For example

我一直在试验 ES6 类,想知道您是否可以动态更改类名?例如

class [Some dynamic name] {}; 

采纳答案by Felix Kling

There is probably a better solution for whatever you are trying to achieve, but you can assign a class expression to an object:

对于您想要实现的任何目标,可能都有更好的解决方案,但您可以为对象分配一个类表达式:

let classes = {};
classes[someName] = class { ... };

This didn't really change in ES2015: if you want to create a dynamically named binding, you have to use an object or some other mapping instead.

这在 ES2015 中并没有真正改变:如果你想创建一个动态命名的绑定,你必须使用一个对象或其他一些映射来代替。

回答by Panu Logic

let C = class
{ // ...
}
Object.defineProperty (C, 'name', {value: 'TheName'});

// test: 
let itsName =  (new C()).constructor.name;
// itsName === 'TheName' -> true

回答by Daerdemandt

There is a pretty simple way to do it:

有一个非常简单的方法来做到这一点:

const nameIt = (name, cls) => ({[name] : class extends cls {}})[name];

Here's the demo.

是演示。

It uses an object literal to define a field with a desired name that would hold a new class. This causes the new class to automatically get the desired name. After we're done with that, we extract that new class and return it.

它使用对象字面量来定义一个具有所需名称的字段,该字段将包含一个新类。这会导致新类自动获得所需的名称。完成后,我们提取该新类并将其返回。

Note the parens around the object literal, so that curly braces don't get mistaken for a code block (...) => {...}.

注意对象字面量周围的括号,以免花括号被误认为是代码块(...) => {...}

Of course, putting an existing class into named fields won't change the class, so this only works if you are creating a new class. If you only need a dynamic name in one place where you define the class you are naming, you can drop an extra inheritance and just go:

当然,将现有类放入命名字段不会更改该类,因此这仅在您创建新类时才有效。如果您只需要在定义要命名的类的地方使用动态名称,则可以删除额外的继承,然后继续:

const myClass = {[name]: class {
    ...
}}[name];

回答by Anibal Ambertin

To take it a bit further playing with dynamic class names and dynamic inheritance, when using babel you can just do something like this:

为了更深入地使用动态类名和动态继承,在使用 babel 时,您可以执行以下操作:

    function withname(name, _parent) {
        return class MyDinamicallyNamedClass extends (_parent||Object) {
            static get name() { return name || _parent.name }
        }
    }

回答by trusktr

One way, even if not ideal, is simple with eval:

一种方法,即使不理想,也很简单eval

~function() {
    const name = "Lorem"

    eval(`
        var ${name} = class ${name} {} 
    `)

    console.log(Lorem) // class Lorem {}
}()

Note, it has to be with var. Using let, const, and plain classinside the evalwon't work.

请注意,它必须与var. 在里面使用let, const, 和 plainclasseval行不通的。

Another way with Function:

另一种方式Function

~function() {
    const name = "Lorem"

    const c = new Function(`
        return class ${name} {}
    `)()

    console.log(c) // class Lorem {}
}()

Sitenote: you can pass scope variables into the Functionand use them inside:

站点注意:您可以将范围变量传递到Function并在其中使用它们:

~function() {
    const name = "Lorem"
    const val = "foo"

    const Class = new Function('val', `
        return class ${name} {
            constructor() {
                console.log( val )
            }
        }
    `)( val )

    console.log(Class) // class Lorem {}
    new Class // "foo"
}()

回答by Greg Woz

The example with which I struggled - resolved in the way below:

我挣扎的例子 - 按以下方式解决:

const models = {
  route: mongoose.model('Route'),
  company: mongoose.model('Company'),
  ...
}

and then:

接着:

const name = 'route'
const record = new models[name]()