Прототипный и функциональный ООП в JavaScript

Каковы преимущества и недостатки каждого типа/подхода в написании объектно-ориентированных скриптов?

Лично я нашел закрытие (функциональный подход) как способ инкапсулировать состояние более естественным и, возможно, более элегантным. Я, однако, слышал, что это использование закрытий медленнее в реализациях JavaScript.

Мне хотелось бы, по крайней мере, узнать, где наиболее подходящий прототипный подход.

Ответ 1

"Функциональный" стиль (большинство людей назвали бы это "традиционным ООП" ):

  • Преимущество: ООП, который работает так, как все (или, по крайней мере, Java-программисты) знакомы, включая "по-настоящему" частные методы и переменные
  • Недостаток: Javascript не был разработан для этого типа ООП, поэтому вы можете прыгать через множество обручей, чтобы заставить его работать. Эти обручи затрудняют отладку, а также добавляют затраты на производительность (хотя точная стоимость будет зависеть от того, как и сколько вы используете)

Стиль прототипа:

  • Преимущество: ООП в том, как был разработан Javascript.
  • Недостаток: Это не то, к чему вы привыкли (если у вас нет фона в других языках наследования protoype)

Итак, если производительность для вас не является огромной проблемой, и вы знакомы только с традиционным ООП... идите на это (у шаблонов проектирования Javascript Design от APress есть хороший шаблон для этого). Но если производительность имеет значение или вы беспокоитесь о дополнительном слое абстракции, усложняющем вашу отладку, найдите время, чтобы узнать, как работает наследование прототипов; вы будете лучшим программистом Javascript для этого.

P.S. Если вы беспокоитесь о том, что у меня нет истинных методов "private" с прототипом, я настоятельно рекомендую прочитать: http://snook.ca/archives/javascript/no-love-for-module-pattern Это дает отличное объяснение, почему истинные члены "private" на самом деле являются плохими (по крайней мере, в большинстве средах разработки JS).

Ответ 2

используйте прототипы для указания наследования объектов. довольно сложно дублировать это с помощью функционального кода (я предполагаю, что вы имеете в виду шаблон, в котором у вас есть закрытые члены в закрытии, и возвращаете объект, содержащий ваших публичных членов?)

function Animal() { }
function Cat () { }

Animal.prototype.sleep = function() { /* blah */ };
Cat.prototype = new Animal;
Cat.prototype.meow = function() { /* blah */ };

var simon = new Cat();
simon.sleep();
simon.meow();