После ряда исследований по этому вопросу я много экспериментировал с шаблонами для упорядочивания кода jQuery (Ребекка Мерфи сделала презентация на этом на конференции jQuery, например).
Вчера я проверил шаблон (показательный) модуля. Результат выглядит немного напоминающим синтаксис YUI:
//global namespace MyNameSpace
if(typeof MNS=="undefined"||!MNS){var MNS={};}
//obfuscate module, just serving as a very simple example
MNS.obfuscate = function(){
//function to create an email address from obfuscated '@'
var email = function(){
$('span.email').each(function(){
var emailAddress = $(this).html().replace(' [ @ ] ','@');
$(this).html('<a href="mailto:' + emailAddress + '">' + emailAddress + '</a>');
});
};
return {
email: email
};
}();
//using the module when the dom ready
jQuery(document).ready(function($){
MNS.obfuscate.email();
});
В конце концов у меня было несколько модулей. Некоторые из них, естественно, включали "частные члены", которые в этом случае означают переменные и/или функции, которые были важны только для других функций в этом модуле и, таким образом, не попадали в оператор return.
Я думал, что связанные части моего кода (все, что связано с поиском, например), объединенное в модуле, имеет смысл, дает всю структуру.
Но после написания этого, я прочитал статью статьи от Джона (Resig), где он также пишет о производительности шаблона модуля:
"Создание функции с множеством свойств прототипа очень, очень быстро, полностью удаляет шаблон модуля и т.д. из воды. Таким образом, если у вас есть функция частого доступа (возвращающая объект) что вы хотите, чтобы люди взаимодействовали, тогда вам в ваших интересах, чтобы свойства объекта находились в цепочке прототипов и создавали его экземпляр. Вот он в коде:
// Very fast
function User(){}
User.prototype = { /* Lots of properties ... */ };
// Very slow
function User(){
return { /* Lots of properties */ };
}
(Джон упоминает, что он не против шаблона модуля "как таковой" - просто чтобы вы знали:)
Тогда я уже не был уверен, что с моим кодом я пойду в правильном направлении. Дело в том, что я не действительно нужен всем частным членам, и я также не думаю, что мне нужно наследование на данный момент. Все, что я хочу сейчас, является читаемым/поддерживаемым шаблоном. Я предполагаю, что это сводится к личным предпочтениям в определенной степени, но я не хочу получать читаемый код, который имеет (довольно серьезные) проблемы с производительностью.
Я не эксперт по JavaScript и, тем более, эксперт, когда дело доходит до тестирования производительности. Итак, во-первых, я не знаю, насколько далеко сказались слова, о которых говорил Джон ( "часто доступная функция (возвращение объекта), с которой вы хотите, чтобы люди взаимодействовали с", множество свойств и т.д.) Применимы к моему коду. Документы, с которыми взаимодействует мой код, не являются огромными, с 100 или 1000 элементами. Так что, возможно, это не проблема.
Но мне показалось, что вместо того, чтобы просто
$('span.email').each(function(){
var emailAddress = $(this).html().replace(' [ @ ] ','@');
$(this).html('<a href="mailto:' + emailAddress + '">' + emailAddress + '</a>');
});
(внутри функции domready), я создаю две "дополнительные" функции, обфускацию и электронную почту из-за использования шаблона модуля. Создание дополнительных функций стоит некоторое время. Вопрос в следующем: будет ли это измеримо в моем случае?
Я не уверен, что в моем примере выше создано закрытие (в интересной записи на форуме jQuery я читал следующее: "Существует философская дискуссия о том, создает ли внутренняя функция замыкание, если оно не ссылаться на что-либо на объект внешней переменной функции..." ), но у меня были замыкания в моем реальном коде. И хотя я не думаю, что у меня были какие-либо циркулярные ссылки, я не знаю, как далеко это может привести к высокому потреблению/проблемам памяти с сборкой мусора.
Мне бы очень хотелось услышать ваши данные об этом и, возможно, увидеть некоторые примеры вашего кода. Кроме того, какие инструменты вы предпочитаете получать информацию о времени выполнения, памяти и использовании ЦП?