Закрытие Компилятор не применяет @const к этому
Я пытаюсь заставить этот кусок кода работать:
/** @constructor */
function Foo()
{
/** @const */
this.bar = 5;
// edit: does now work
// this.bar = 3;
}
var f = new Foo();
// should be inlined (like other constants)
alert(f.bar);
Я уже пытался добавить больше аннотаций (типы, конструктор), @enum
вместо @const
(за this.bar
), me = this
все это не имело никакого эффекта.
Страница справки не очень помогла в этом.
Есть ли способ заставить это работать? Если нет, то почему?
3 ответа
Компилятор не имеет никакой общей логики "встроенных свойств". Вы можете сделать это встроенным в режиме ADVANCED, используя функцию-прототип:
/** @constructor */
function Foo() {}
Foo.prototype.bar = function() { return 5 };
var f = new Foo();
alert(f.bar());
будет компилировать в:
alert(5);
Компилятор сделает это, если существует только одно определение метода "bar", а "bar" используется только в выражении вызова. Логика, используемая для этого, не является правильной в общем случае (если вызов находится на объекте, который не определяет "бар", который вызовет вызов). Это, однако, считается "достаточно безопасным".
Добавление /** @constructor */
работает:
/** @constructor */
function Foo()
{
/** @const */
this.bar = 5;
// cc does not complain
//this.bar = 3;
}
var f = new Foo();
// should be inlined
alert(f.bar);
компилируется в:
alert((new function() { this.a = 5 }).a);
если я раскомментирую this.bar = 3;
я получил это ожидаемое предупреждение:
JSC_CONSTANT_PROPERTY_REASSIGNED_VALUE: constant property bar assigned a value more than once at line 9 character 0
this.bar = 3;
^
В документации сказано, что:
Компилятор выдает предупреждение, если переменной, отмеченной @const, присваивается значение более одного раза. If the variable is an object, note that the compiler does not prohibit changes to the properties of the object.
PS: вы включили следующий код в свой скрипт или HTML-страницу?
<script src="closure-library/closure/goog/base.js"></script>