Использование констант пространства имен в качестве ключей объекта?

Я хочу использовать строковые константы вместо прямых строк в моих объектах Javascript (при определении ключей параметров и т. д.). Цель состоит в том, чтобы мой код был проиндексирован IDE, имел предложения, автокоррекции/дополнения, все безошибочные плюсы.

Я хочу определить явные ключи для конструктора этого класса EPPZObject, поэтому я сделал:

var EPPZ =
{
    width: 'width',
    height: 'height'
}

var EPPZObject = Class.extend
({

    construct: function(parameters)
    {
        // Constant usage works fine here.
        log(parameters[EPPZ.width]);
        log(parameters[EPPZ.height]);
    }

});

В клиентском коде я также могу использовать константы:

log(EPPZ.width); // Logs 'width' just fine.
log(EPPZ.height); // Logs 'height' just fine.

Но когда я хочу использовать константы при построении (на самом деле в этом весь смысл), то это просто не работает:

var objectThatWorks = new EPPZObject(
        {
            'width' : '9',
            'height' : '9',
        });

var objectThatNotWorks = new EPPZObject(
        {
            EPPZ.width : '9',
            EPPZ.height : '9',
        });

В нем говорится:

Uncaught SyntaxError: Unexpected token . 

Как преодолеть это? Есть ли такое же чистое решение для использования констант?


person Geri Borbás    schedule 02.01.2014    source источник
comment
Возможно вопрос How to use expressions as associative array keys at declaration time?   -  person Geri Borbás    schedule 03.01.2014
comment
Вы не можете использовать переменные в литералах объектов. Может быть, вам стоит поискать какой-нибудь макропрепроцессор, вместо того, чтобы определять имена как js-переменные. Эти константы никогда не изменятся, так зачем делать их динамическими?   -  person Bergi    schedule 03.01.2014
comment
Я просто хочу, чтобы моя IDE (PHPStorm) автоматически исправляла/автопредлагала при вводе конструкторов. Я хочу, чтобы все ключи параметров были проиндексированы. Бьюсь об заклад, препроцессор Foreign не сделает этого за меня.   -  person Geri Borbás    schedule 03.01.2014
comment
В JavaScript нет такой вещи, как класс   -  person Alex Shilman    schedule 03.01.2014
comment
@Alex: function Class(){}Class.prototype.construct=function(){};Class.extend=function(e){var t=function(){if(arguments[0]!==Class){this .construct.apply(this,arguments)}};var n=new this(Class);var r=this.prototype;for(var i in e){var s=e[i];if(s instanceof Function) s.$=r;n[i]=s}t.prototype=n;t.extend=this.extend;возврат t}   -  person Geri Borbás    schedule 03.01.2014
comment
Да, я знаю. Но это заказное. По умолчанию JavaScript не имеет объекта класса.   -  person Alex Shilman    schedule 03.01.2014
comment
@Geri: вам нужно передавать объекты вашим конструкторам? Было бы проще [вводить], если бы у вас было несколько параметров. Ваша IDE должна показывать вам их имена и документы при вызове конструктора.   -  person Bergi    schedule 03.01.2014
comment
@AlexShilman: это имеет значение? Это не входит в рамки этого вопроса.   -  person Bergi    schedule 03.01.2014
comment
Яп, правда. Вопрос не относится к моей первоначальной проблеме. Скоро редактирую. Документы сделают это сейчас, спасибо, ребята.   -  person Geri Borbás    schedule 03.01.2014
comment
как насчет параметров[EPPZ['width']]   -  person Alex Shilman    schedule 03.01.2014
comment
Я могу использовать его нормально при ссылке, проблематичной частью является время объявления объекта параметра.   -  person Geri Borbás    schedule 03.01.2014
comment
На самом деле я просто предпочитаю читаемые/явные/защищенные от ошибок интерфейсы классов вместо документации/комментариев, свободных параметров, списков параметров и так далее. Довольно болезненно создавать дизайн на Javascript после того, как поболтался с Objective-C. Даже в PHP есть лучшие шаблоны. :(   -  person Geri Borbás    schedule 03.01.2014


Ответы (2)


Можно обойти действительно странным образом. Не уверен, что буду использовать это в производстве.

Использование вспомогательного объекта, который «переводит» параметры в объект:

var Parameters = Class.extend
({
    construct: function(parameters)
    {
        for (var index = 0; index < parameters.length; index += 2)
        { this[parameters[index]] = parameters[index+1]; }
    }
});

Теперь я могу создавать объекты почти так, как хотел...

var object = new EPPZObject(new Parameters(
[
    EPPZ.width, 8,
    EPPZ.height, 9,
]));

... но также добавил шаблонный код :(

person Geri Borbás    schedule 03.01.2014

Вы не можете сделать синглтон вот так?:

var EPPZ = {
        width : '9',
        height : '9'
};

а потом может быть

var objectThatWorks = new Object();
objectThatWorks.width = EPPZ.width;
objectThatWorks.height = EPPZ.height;

РЕДАКТИРОВАТЬ

Вы пробовали прототипировать?

EPPZObject.prototype.width = EPPZ.width;
person Santiago Rebella    schedule 03.01.2014
comment
Я должен использовать константы для ключей, а не для значений. Но это что-то близкое к тому, что я только что придумал -› использование промежуточного объекта. - person Geri Borbás; 03.01.2014