jquery .val() и компилятор закрытия Google

Я хочу выбрать первый вариант в элементе управления, поэтому я пишу:

$("#MySelect").val($("#MySelect option:first").val());

Теперь скопируйте и вставьте следующее в компилятор закрытия Google:

// ==ClosureCompiler==
// @output_file_name default.js
// @compilation_level ADVANCED_OPTIMIZATIONS
// @externs_url http://closure-compiler.googlecode.com/svn/trunk/contrib/externs/jquery-1.7.js
// ==/ClosureCompiler==

$("#MySelect").val($("#MySelect option:first").val());

Вы получите эту ошибку:

введите здесь описание изображения

Я не понимаю, почему компилятор жалуется! В чем проблема?

Спасибо за ваши предложения.


person frenchie    schedule 10.08.2012    source источник
comment
Вы могли бы сделать это $("#MySelect").prop("selectedIndex", 0 )​​​​   -  person Esailija    schedule 11.08.2012
comment
Похоже, установлено, что внутренний метод .val() потенциально может возвращать тип, не соответствующий тому, что внешний метод .val() ожидает в качестве параметра. Например, если бы он возвращал объект jQuery, это было бы неправильно, за исключением того, что, конечно, мы знаем, что .val() возвращает объект jQuery только при вызове с параметром, поэтому в вашем коде это никогда не произойдет для внутреннего .val(). ..   -  person nnnnnn    schedule 11.08.2012
comment
Вы можете использовать index() вместо val()   -  person wirey00    schedule 11.08.2012
comment
@Esailija: вы должны отметить свой комментарий как ответ; оно работает.   -  person frenchie    schedule 11.08.2012
comment
Я не думаю, что это действительно ответ. Это обходной путь, но вам не нужно менять идеальный код только для того, чтобы сделать какой-то инструмент счастливым.   -  person ThiefMaster    schedule 11.08.2012


Ответы (2)


Вы можете сделать это $("#MySelect").prop("selectedIndex", 0)​​​​. Это проще и проходит компилятор закрытия.

person Esailija    schedule 10.08.2012

Многие методы jQuery возвращают разные типы в зависимости от количества и типа входных параметров. Такое поведение похоже на перегрузку функций в традиционном языке. Однако JavaScript не поддерживает традиционную перегрузку функций, и jQuery имитирует поведение, проверяя аргументы функции.

Вот как метод будет аннотирован для .val, если будет поддерживаться перегрузка функций:

/** @return {number|string|Array.<string>} */
jQuery.prototype.val = function() {};

/**
 * @param {number|string|Array.<string>|function(number, *)} newVal
 * @return {!jQuery}
 */
jQuery.prototype.val = function(newVal) {};

Поскольку перегрузки функций нет, фактическая подпись для .val представляет собой комбинацию обоих вариантов использования:

/**
 * @param {(number|string|Array.<string>|function(number, *))=} newVal
 * @return {!jQuery|number|string|Array.<string>|function(number, *)}
 */
jQuery.prototype.val = function(newVal) {};

Из-за этого, если вы хотите использовать возвращаемое значение .val в качестве входных данных для отдельного вызова .val, вы должны ввести исходное возвращаемое значение, чтобы указать, какое использование вы ожидаете:

$("#MySelect").val(
    /** @type {number|string|Array.<string>} */
    ($("#MySelect option:first").val()) //note the extra parens
);

Это поведение описано в комментарии вверху файла externs jQuery: http://code.google.com/p/closure-compiler/source/browse/trunk/contrib/externs/jquery-1.7..js#20

person Chad Killingsworth    schedule 13.08.2012