"Забытый стиль ООП в Smalltalk"


Уже долгое время я пытаюсь разобраться в том, как же правильно “готовить” этот самый ООП, и долгое время смотрел в основном книги, посвященный паттернам проектирования. Но когда говорят о развитии ООП, то часто упоминаются язык, который оказал значительное влияние на объектно-ориентированный подход - Smalltalk и его создатель - Алан Кей. В какой-то момент возникла мысль - возможно стоит взглянуть на, так сказать, исток всего этого подхода (да, формально первым языком, использующим концепцию объектов была Simula, но именно Smalltalk популяризовал ООП), чтобы приблизиться к пониманию того, каким он задумывался изначально.

Первое знакомство вызвало небольшой шок - ООП в Smalltalk вообще совсем не похоже на современные языки. Если, считать, например, Java за “дефолтный” ООП язык, то между ними мало общего, и дело не только в синтаксисе (хотя и в нем тоже) - в первую очередь динамическая типизация, что делает Smalltalk ближе к какому-нибудь Python или даже Elixir, с последним у них схожесть в плане акторной модели, но об это позже.

Если вернуться опять же к Java, то можно вспомнить, сколько там различного синтаксиса для “построения” ООП - все эти “abstract”, “interface” и т.д. В противоположность, как утверждается в “фичах” Pharo (современный диалект Smalltalk), весь синтаксис насчитывает всего 6(!) ключевых слов и может уместиться на почтовой открытке. Такой минимализм достигается как раз за счёт динамизма языка, и, как следствие, “позднего связывания” компонентов. Язык не требует строгого описания иерархий и отношений между ними, поэтому большинство популярных “паттернов проектирования” будут иметь гораздо меньшее значение в Smalltakl.

Объекты по-видимому никогда не должны были иметь сложный интерфейс и внешней и закрытой частью. В инкапсуляции гораздо более важной частью будет именно “сокрытие” данных (а не связь данных и их методов). Метафора, которая предлагается Аланом Кеем - каждый объект представляет собой небольшой самодостаточный “компьютер”. Детали реализации скрыты от пользователя, позволяя объекту самостоятельно разобраться с содержанием сообщения.

Поэтому главное - это не объекты, но передача сообщений между ними. “Message-passing oriented programming” - объекты, это независмые сущности, которые асинхронно обмениваются сообщениями - изменяя свое состояние/поведения, а иногда передавая сообщение другим объектам (наследование - частный случай такого делегирования).

Ещё более странно, что настоящие наследники стиля ООП-Smalltalk - это языки и фреймворки ориентированные акторную модель. Эта модель гораздо сильнее ассоциируется с функциональным программированием (и в частности - реактивным программированием), в частности с Erlang/Elixir и наиболее известным “акторным” фреймворком - Akka, который в основном написан на Scala. Некоторые говорят, что похожий стиль ООП наблюдается в Ruby, и он значительно ближе к Smalltalk чем в остальных современных языках (к сожалению, я не знаком с Ruby).

Если кому-то хочется потестить Smalltalk и посмотреть как ещё может выглядеть ООП-код, то у него есть современные бесплатные реализации: Squeak/Smalltalk и уже упомянутый Pharo.

Кстати - еще одна “фишка” что у Squeak что у Pharo - это интеграция языка вместе со специально построенной прямо для него IDE.