Объявление статических констант в классах ES6?
Я хочу реализовать константы в class, потому что именно там имеет смысл найти их в коде.
до сих пор я реализовывал следующий обходной путь со статическими методами:
class MyClass {
static constant1() { return 33; }
static constant2() { return 2; }
// ...
}
Я знаю, что есть возможность возиться с прототипами, но многие рекомендуют против этого.
есть ли лучший способ реализовать константы в классах ES6?
8 ответов:
вот несколько вещей, которые вы могли бы сделать:
экспорт a
constС модуль. В зависимости от вашего варианта использования, вы можете просто:export const constant1 = 33;и импортировать из модуля, где это необходимо. Или, основываясь на вашей идее статического метода, вы можете объявить
staticметод доступа get:const constant1 = 33, constant2 = 2; class Example { static get constant1() { return constant1; } static get constant2() { return constant2; } }таким образом, вам не понадобится скобки:
const one = Example.constant1;тогда, как вы говорите, так как
classэто просто синтаксический сахар для функции, которую вы можете просто добавить свойство без записи, например:class Example { } Object.defineProperty(Example, 'constant1', { value: 33, writable : false, enumerable : true, configurable : false }); Example.constant1; // 33 Example.constant1 = 15; // TypeErrorбыло бы неплохо, если бы мы могли просто сделать что-то вроде:
class Example { static const constant1 = 33; }но, к сожалению, этот класса синтаксис только в предложении ES7, и даже тогда он не позволит добавить
constв собственность.
я использую
babelи следующий синтаксис работает для меня:class MyClass { static constant1 = 33; static constant2 = { case1: 1, case2: 2, }; // ... } MyClass.constant1 === 33 MyClass.constant2.case1 === 1пожалуйста, учтите, что вам нужен предустановленных
"stage-0".
Чтобы установить его:npm install --save-dev babel-preset-stage-0 // in .babelrc { "presets": ["stage-0"] }обновление:
в настоящее время использовать
stage-2
In документ говорится:
нет (намеренно) прямого декларативного способа определения свойств класса данных прототипа (кроме методов) или свойства экземпляра
это означает, что это намеренно так.
может быть, вы можете определить переменную в конструкторе?
constructor(){ this.key = value }
также можно использовать
Object.freezeна вас класс (es6) / конструктор функция(es5) объект, чтобы сделать его неизменяемым:class MyConstants {} MyConstants.staticValue = 3; MyConstants.staticMethod = function() { return 4; } Object.freeze(MyConstants); // after the freeze, any attempts of altering the MyConstants class will have no result // (either trying to alter, add or delete a property) MyConstants.staticValue === 3; // true MyConstants.staticValue = 55; // will have no effect MyConstants.staticValue === 3; // true MyConstants.otherStaticValue = "other" // will have no effect MyConstants.otherStaticValue === undefined // true delete MyConstants.staticMethod // false typeof(MyConstants.staticMethod) === "function" // trueпопытка изменить класс даст вам soft-fail (не будет бросать никаких ошибок, это просто не будет иметь никакого эффекта).
как https://stackoverflow.com/users/2784136/rodrigo-botti сказал, Я думаю, вы ищете
Object.freeze(). Вот пример класса с неизменяемой статикой:class User { constructor(username, age) { if (age < User.minimumAge) { throw new Error('You are too young to be here!'); } this.username = username; this.age = age; this.state = 'active'; } } User.minimumAge = 16; User.validStates = ['active', 'inactive', 'archived']; deepFreeze(User); function deepFreeze(value) { if (typeof value === 'object' && value !== null) { Object.freeze(value); Object.getOwnPropertyNames(value).forEach(property => { deepFreeze(value[property]); }); } return value; }
class Whatever { static get MyConst() { return 10; } } let a = Whatever.MyConst;Кажется, работает для меня.
вы можете создать способ определения статических констант в классе, используя нечетную функцию классов ES6. Поскольку статика наследуется их подклассами, вы можете сделать следующее:
const withConsts = (map, BaseClass = Object) => { class ConstClass extends BaseClass { } Object.keys(map).forEach(key => { Object.defineProperty(ConstClass, key, { value: map[key], writable : false, enumerable : true, configurable : false }); }); return ConstClass; }; class MyClass extends withConsts({ MY_CONST: 'this is defined' }) { foo() { console.log(MyClass.MY_CONST); } }
вот еще один способ вы можете сделать
/* one more way of declaring constants in a class, Note - the constants have to be declared after the class is defined */ class Auto{ //other methods } Auto.CONSTANT1 = "const1"; Auto.CONSTANT2 = "const2"; console.log(Auto.CONSTANT1) console.log(Auto.CONSTANT2);Примечание - порядок важен, вы не можете иметь константы выше
использование приставка.журнал (авто.CONSTANT1);
Comments