LINUX.ORG.RU

Существуют ли иные модели ООП?

 , ,


1

3

На сегодняшний день известно 2 модели ООП. Назовем их условно, «сильная» и «слабая».

Первая — смолтоковская модель, основанная на, воистину, величайших идеях Алана Кея, в первую очередь — позднее связывание и концентрация на сообщениях.

Вторая — основанная на лексических замыканиях.

К сожалению, вторая модель получила наибольшее распространение в современных языках программирования. Первая нашла свое воплощение лишь в очень малом количестве ЯП, из мейнстримных я знаю только JS и Ruby. Видимо, основная причина в трудностях эффективной реализации мощной модели, хотя, пример JS заставляет усомниться в этом. Другой причиной, может быть то, что средний программист не может понять сильную модель, тогда как слабую понимают почти все.

А вопрос такой: есть ли какая-нибудь альтернативная модель, некий третий путь. Тут следует пояснить, наверное, что я не провожу различия между смолтоковской классовой(smalltalk, ruby) и прототипной(js, self, io) моделями, условно считаем, что это то же самое, также я не провожу различия между замыканиями и java-like-классами, в данном случае (т.е. модель scheme в контексте примеров модели вычислений с окружениями из SICP === java-style etc), нутыпонел — я обобщил. Может быть что-то еще, принципиально отличающееся от этих двух, есть такое?



Последнее исправление: oop (всего исправлений: 1)

Ответ на: комментарий от dizza

Второй пример из разряда quick-and-dirty, такое не годится. Первый пример правильный, но таки да, раздутый, поэтому нужен сахарок для классов.

Семантически, разницы нет. Если нет разницы, зачем писать больше? К тому же, программист сбит с толку. Он «думает» что есть какие то там классы, отличные от простых объектов, что мешает думать в контексте метаобъектной парадигмы.

oop
() автор топика
Ответ на: комментарий от oop

Ой, чувак, все гораздо сложнее, чем «семантической разницы нет». Первый код содержит intention по поводу того, какие есть отношение между обьектами, кто там предок, какое состояние эталонное и так далее. Второй код - простыня. Короче, первый код более поддерживаемый.

dizza ★★★★★
()
Последнее исправление: dizza (всего исправлений: 1)
Ответ на: комментарий от dizza

какие есть отношение между обьектами, кто там предок, какое состояние эталонное и так далее.

все это есть и во втором коде.

цикл и ветвление семантически эквиваленты оператору goto

они семантически не эквивадентны goto, а есть лишь частные случаи его.

, давайте только его оставим.

я не против

oop
() автор топика
Ответ на: комментарий от oop

все это есть и во втором коде.

Оно частично в коде, частично у тебя в голове. А в первом случае все в коде. Короче тебе нужно поднабраться опыта поддержки софта, тогда поймешь о чем речь.

dizza ★★★★★
()
Ответ на: комментарий от dizza

Первый код содержит intention по поводу того, какие есть отношение между обьектами, кто там предок, какое состояние эталонное и так далее

точней, все есть кроме последнего. Легко решаемо синтаксическими соглашениями. Собственно классы в данном случае, это и есть синтаксическое соглашение, только раздутое.

oop
() автор топика
Ответ на: комментарий от stevejobs

чтобы установить общий стандарт

Ну да. То-то в C++ почти до 2000 года классы были, но толку не было, так как MFC, OWL, Qt, и ещё полсотни других были друг с другом не совместимы (включая такие примитивы, как строки, списки, массивы).

В то время как GObject (+GIR) действительно задаёт стандарт на все библиотеки, использующие его. В том смысле, что в них работает интроспекция, наследование, единые базовые типы.

monk ★★★★★
()
Ответ на: комментарий от oop

А где вы нашли переопределение класса в моем коде? Я изменил только одно поле.

Это и есть переопределение класса. Звучит как «Где вы нашли переопределение модуля? Я заменил только одну функцию».

monk ★★★★★
()
Ответ на: комментарий от monk

С замыканием эта фишка ен прокатит, так как нет доступа к окружениям из-вне. Это во первых. Во вторых — есть разница, перееопределить ли функцию представляющую класс, тоесть, класс целиком, и переопределить одно поле.

oop
() автор топика
Ответ на: комментарий от oop

С замыканием эта фишка ен прокатит, так как нет доступа к окружениям из-вне.

Смотря как напишешь. Вот пример, где меняется класс объекта. Но можно менять и описание класса: (hash-ref prototype my-class%) вполне доступен.

В случае CLOS вообще выполняешь defclass с новыми суперклассом (и, возможно, полями) и работаешь дальше (CLOS — тоже макросы + замыкания).

#lang racket

(define prototype (make-hash))

(define (pget pobject key)
  (hash-ref (get-field __this__ pobject) 
            key
            (λ ()
              (for/or ([h (in-list (get-field __proto__ pobject))])
                (hash-ref h key #f)))))

(define (psend pobject key . args)
  (apply (pget pobject key) pobject args))

(define (pset! pobject key value)
  (hash-set! (get-field __this__ pobject) key value))

(define prototype% (class object% (super-new)
                     (field [__proto__ (make-hash)]
                            [__this__ (make-hash)])))

(define-syntax-rule (proto-class super (proto-fields ...) (this-fields ...) rest ...)
  (let* ([proto (cons
                 (hash-copy (hash proto-fields ...))
                 (hash-ref prototype super null))]
         [res (class super
               (inherit-field __proto__ __this__)
               rest ...
               (super-new)
               (set! __proto__ proto)
               (set! __this__
                     (hash-copy
                      (hash this-fields ...))))])
    (hash-set! prototype res proto)
    res))

(define man%
  (proto-class prototype%               
               ('legs 2
                'hands 2
                'head 1
                'fullName (λ (this) (string-append (pget this 'name) 
                                                   " " 
                                                   (pget this 'lastName))))
               ()))

(define boy%
  (proto-class man%
               ('power 'strong
                'sex 'male)
               ('name name
                'lastName lastname)
               (init-field name lastname)))

(define girl%
  (proto-class man%
               ('power 'weak
                'sex 'female)
               ('name name
                'lastName lastname)
               (init-field name lastname)))

(define boy (make-object boy% "Jack" "Smith"))

(pset! boy 'name "Jane")
(pset! boy 'sex 'female)

(set-field! __proto__ boy (hash-ref prototype girl%))

(hash-set! (car (hash-ref prototype man%)) 'heart 'warm)
(hash-set! (car (hash-ref prototype girl%)) 'tits #t)

(displayln (~v (pget boy 'hands)
               (pget boy 'legs)
               (pget boy 'head)
               (psend boy 'fullName)
               (pget boy 'power)
               (pget boy 'sex)
               (pget boy 'tits)
               (pget boy 'heart)))

;;; выводит
2 2 1 "Jane Smith" 'weak 'female #t 'warm
monk ★★★★★
()
Ответ на: комментарий от oop

функцию представляющую класс

Это только в JS функция и класс — одно и то же. Обычно класс — структура с полями. Так вот, добавить поле == переопределить структуру.

monk ★★★★★
()

есть. я тебе бусы, ты мне банан. Пару тонн, прямо с плантации.

darkenshvein ★★★★★
()
Ответ на: комментарий от monk

Это только в JS функция и класс — одно и то же. Обычно класс — структура с полями. Так вот, добавить поле == переопределить структуру.

В JS класс и ф-ция не одно и тоже. Класс это функция + окружение, которое наследуется экземплярами.

А то что ты написал, не имеет отношения к вопросу. Я говорил об обычной модели на замыканиях, типа той которая с банковскими счетами в SICP. Чистые классы на замыканиях, а не батарейки и макросы.

oop
() автор топика
Ответ на: комментарий от oop

Чистые классы на замыканиях

Могу то же самое на замыканиях без racket/class переписать.

Я говорил об обычной модели на замыканиях, типа той которая с банковскими счетами в SICP.

Если ты про

(define (make-account balance)
  (define (withdraw amount)
    (if (>= balance amount)
        (begin (set! balance (- balance amount))
               balance)
        "Insufficient funds"))
  (define (deposit amount)
    (set! balance (+ balance amount))
    balance)
  (define (dispatch m)
    (cond ((eq? m 'withdraw) withdraw)
          ((eq? m 'deposit) deposit)
          (else (error "Unknown request -- MAKE-ACCOUNT"
                       m))))
  dispatch)

то здесь нет ни класса, ни, тем более, суперкласса. Изменение методов добавляется тривиально

(define (make-account balance)
  (define (withdraw amount)
    (if (>= balance amount)
        (begin (set! balance (- balance amount))
               balance)
        "Insufficient funds"))
  (define (deposit amount)
    (set! balance (+ balance amount))
    balance)
  (define (dispatch m)
    (cond ((eq? m 'withdraw) withdraw)
          ((eq? m 'deposit) deposit)
          ((eq? m 'set-withdraw!) 
           (lambda (new-body)
             (set! withdraw 
               (lambda () 
                 (set! balance (new-body balance))))))
          (else (error "Unknown request -- MAKE-ACCOUNT"
                       m))))
  dispatch)

monk ★★★★★
()
Последнее исправление: monk (всего исправлений: 1)
Ответ на: комментарий от monk

здесь нет ни класса, ни, тем более, суперкласса

Класс тут есть makeAccount = new Account, разница только в сахаре

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

oop
() автор топика

Заведи свой канал подкастов «Посиделки с анонiмусом».

Deleted
()
Ответ на: комментарий от oop

добавить его сверх существующего кода, не переписывая его

Можно написать ООП с классами/суперклассами на замыканиях с возможностью изменения суперкласса. Но на scheme так никто делать не будет (разве что в качестве студенческой курсовой), так как нарушает основную идею: интерфейс объявляется единожды и изменяться не должен.

В Common Lisp (CLOS) я уже писал: выполняешь (defclass my-class (new-superclass) ...) и всё работает как ожидается. Кроме того суперклассов может быть много.

monk ★★★★★
()
Ответ на: комментарий от monk

Можно написать ООП с классами/суперклассами на замыканиях с возможностью изменения суперкласса

будет возможность добавления суперкласса над суперклассом неограниченно вверх? Что то я в этом сомневаюсь. Сама модель лексических замыканий противоречит этому.

oop
() автор топика
Ответ на: комментарий от oop

кто может — тот возьмет более подходящий инструмент, основная же масса будет писать дефолтную хрень

Стесняюсь спросить, а к какой группе ты себя причисляешь?

kravich ★★★★
()
Ответ на: комментарий от oop

будет возможность добавления суперкласса над суперклассом неограниченно вверх?

(define (make-class super-class slots dispatch)
  (lambda (action . slots-values)
     (cond action
       ((new)
        (define data (make-data slots slot-values))
        (define (real-dispatch m)
          (cond
            ((eq? m '%set-method!) 
              (lambda (new) (change-dispatch! dispatch m new)))
            ((eq? m '%change-super!)
              (lambda (new) (set! super-class new)))
            ((dispatch m) => 
              (lambda (x) (apply x data))
            (((super-class 'dispatch) m) => 
              (lambda (x) (apply x data)))
            (else (error 'bad-method)))))
       ((dispatch) dispatch)
       ((change-super!) (lambda (new) (set! super-class new))))))

Дальше

(define my-class 
  (make-class #f '(a b)
    (lambda (m)
       (case m
          ((method1) (lambda (a b) 
           (lambda (x) (+ x a b))))))))

(define obj ((my-class 'new) 1 2))
(obj 'method1 3) ; -> 6

(define super-class
  (make-class #f '()
    (lambda (m)
       (case m
          ((method2) (lambda () 
           (lambda (x) (+ x 1))))))))

((my-class 'change-super) super-class)
(obj 'method2 1) ; -> 2

P.S. Возможны опечатки

monk ★★★★★
()
Ответ на: комментарий от erzent

C++ ООП, в программе бауманки даже есть....

Ах, ну раз в программе бауманки есть... Алан Кей говорит, что в C++ нет ООП, и, как создателю термина ООП, я ему верю куда больше, чем недоучке-админу, который постоянно ноет из-за маленького чл^W^Wнизкой зарплаты.

hateyoufeel ★★★★★
()
Ответ на: комментарий от erzent

Недоучка не недоучка, а получаю з\п выше рыночной на 30 шт по городу, так что закрой рот и завидуй молча.

И? Ты тут зарплатой будешь мериться? У многих тут длиннее, поверь, но не в этом суть. Твой оклад вообще слабо кореллирует с компетентностью, особенно в случае с РФ, где «даже кухарка может управлять государством». Лично твоя компетентность, к слову, под большим сомнением, и не только в области программирования.

hateyoufeel ★★★★★
()
Ответ на: комментарий от oop

можно сделать на данном интерфейсе?

Разумеется. При этом в obj появятся методы от super-puper-class

monk ★★★★★
()
Ответ на: комментарий от erzent

а я не программист

Да, мы уже это давно заметили. Не пиши больше херню про программирование, пожалуйста.

я дал ссылку на гугл

Ссылка!

Я тоже дал ссылку на гугл. Если исходить из этой ссылки, в c++ есть большие сиськи.

ты несёшь бред мне от себя

Я несу бред во имя луны! А, вообще, я запомню этот оборот на будущее.

hateyoufeel ★★★★★
()
Последнее исправление: hateyoufeel (всего исправлений: 1)
Ответ на: комментарий от erzent

а получаю з\п выше рыночной на 30 шт по городу,

Учитывая, что ты админишко, и вспоминая все твои сопли и нытик-треды, легко сделать вывод, что ты в очень глубокой жопе. Полагаю, у тебя даже $6000 в месяц не получается.

anonymous
()
Ответ на: комментарий от erzent

С++ есть большие сиськи, у нас на работе стажёрка у программистов, барышня с 4 размером.

И на основании этих данных твоё мнение по части ООП вообще и C++ в частности является весомым?

hateyoufeel ★★★★★
()
Ответ на: комментарий от erzent

Не, ну если тебе не западло себя с дворниками и вахтерами сравнивать - то столько ты, значит, и стоишь. Только IT-специалистом себя не называй тогда, не смеши публику.

anonymous
()
Ответ на: комментарий от erzent

только вот средняя по городу 35-40, а не 300 шт.
получаю з\п выше рыночной на 30 шт по городу

То есть тебе 27, ты женат, у тебя есть дети, а ты получаешь всего 65 тысяч (это, кстати, до или после вычета налогов)? Почему твоя жена от тебя ещё не сбежала? Она что, безногий карлик?

anonymous
()
Ответ на: комментарий от anonymous

Каких налогов? В России все налоги платит работодатель, если мы говорим о наемном труде.

Ерзент нашел что-то более высокооплачиваемое на рынке, чем услуги студента-эникея. Но завидовать тут нечему, потому как уволят его скоро либо сам свалит. А начальство всегда будет иметь повод его трахнуть любым удобным для себя способом, и оправданием будут как раз эти лишние 30 шт:)

К тому же бедолаге всю жизнь придется кормить спиногрызов и завидовать свободным от подобных проблем людям.

Ну и btrfs конечно в продакшене, сами понимаете, долго такое продолжаться не может:)

anonymous
()
Ответ на: комментарий от anonymous

Каких налогов? В России все налоги платит работодатель, если мы говорим о наемном труде.

И? Официальная зарплата указывается до вычета налогов :)

anonymous
()

легко. считай:

1) Simula и C++, Java, C#, D, Delphi, ...

2) классы как замыкания в Scheme, прототипы в Self, IO, JavaScript

3) классы как биологическая клетка в SmallTalk и диспетчеризация по :doesNotUnderstand (а также Objective C, и Swift). оно же: Common Lisp и Flavors

4) Common Lisp и CLOS: мультиметоды, родовые функции, метаобъектный протокол, динамика, рефлексия, аспекты. сменить тип класса в рантайме.

6) Eiffel: шаблоны и множественное наследование, но не как в С++. SCOOP, агенты. контракты.

7) COS из например http://ldeniau.web.cern.ch/ldeniau/html/oopc/oopc.html http://ldeniau.web.cern.ch/ldeniau/cos.html .

8) Модульность в стиле Oberon-2, Component Pascal, Modula-2.

9) ... (например, свой велосипед для форт-систем или для лиспов) ...

10) GoLang — ООП без объектов

11) Хаскель и типы классов вместо объектов.

12) Эрланг и сообщения и акторы вместо объектов.

--

Видишь, сколько РАЗНЫХ объектных моделей тебе насчитал ??? Подумай, чем они отличаются.

anonymous
()
Ответ на: комментарий от monk

То-то в C++ почти до 2000 года классы были, но толку не было

ну, если вспомнить полуось и SOM, то там в C++ (и в plain C) были метаклассы, наследование, полиморфизм, и т.п.

вот кстати, SOM — пример объектной модели (системы), не зависимой от языка.

anonymous
()
Ответ на: комментарий от oop

можносделать буханкотроллейбус

но зачем? что при таком финте происходит с системой типов?

anonymous
()
Ответ на: комментарий от anonymous

И? Официальная зарплата указывается до вычета налогов :)

Чушь не пори, всегда указывается сколько ты будешь получать чистыми на руки.

anonymous
()
Ответ на: можносделать буханкотроллейбус от anonymous

но зачем? что при таком финте происходит с системой типов?

Естественно, добавляется родительский класс в начало иерархии. Можно придумать извращённый пример использования: в зависимости от переменной $DISPLAY инициализировать корень классом для Gtk или ncurses. Хотя, с точки зрения здравомыслия, агрегирование во таких ситуациях логичней.

monk ★★★★★
()
Ответ на: комментарий от anonymous

Теперь любой полиморфизм будет считаться объектной моделью? Боюсь, твой пост не укладывается в общепринятую терминологию.

fmdw
()
Ответ на: комментарий от anonymous

всегда указывается сколько ты будешь получать чистыми на руки.

Может, он давно в РФ не жил. Я других стран не знаю, где указывали бы net а не gross, потому как размер налогов слишком сильно зависит от личных обстоятельств каждого работника.

anonymous
()
Ответ на: комментарий от monk

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

вся эта история с полуосью и её классным, но закрытым API довольно мутная. межделмаш вон несколько мегабаксов потратил на свой полумух, прежде чем начал в пингвинукс вливать.

а мелкомягкие между тем тратят свои мегабаксы на прорывные технологии: изобретают инновационный джойстик за $100M и ещё столько же на кинект

очень разумное вложение капиталов, ага. буду эти две ссылки всем наивным либерастишкам в морду тыкать, когда они будут выступать на тему: «как эффективно корпорации распоряжаются ресурсами, финансируют R&D, внедряют такие прям прорывные, очень смелые инновации».

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

ты будешь смеятся, но и у лиспа в геймдеве в 80х, даже до середины 90х были шансы: я про Interactive Fiction, Inform и его Zork-а ( Zork VM был раскручен из лиспа и вполне себе был историей успеха: портирование с миниэвм на 8-битки 80-х. см. историю информа и зорка: словарь (ищи по MDL Lisp и ZIL), затеряные сорцы, ZIL

чорт, даже в журнале «Байт» в середине 80-х писали про среду для разработки IF, на лиспе.

вот прикинь «альтернативную историю»: если эти теперешние $100M на джойстик вложить тогда в штуку вроде Compreno + Gellish инглиш + Natural Business English + SHRLDU, или хотя бы в «более лучший лисп».

да даже хотя бы в более зрелую реализацию CL + открыть исходники ещё тогда. или в те же аппаратные Dataflow лисп.

а то вот обещает HP нам мемристоры и свою Maшину, да не сильно торопится — см. в новостях: мемристоры собираются производить в партнёрстве с SK Hynix, а тем надо в первую очередь свою DRAM протолкнуть.

отчего люди не летают, не летают словно птицы? отвечает Сергей Шнуров и группа «Ленинград».

anonymous
()
Ответ на: комментарий от monk

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

anonymous
()
Ответ на: комментарий от anonymous

Сеттинг: альт. хистори и попаданко. «Если бы у бабушки было <далее список>, она бы стала <censored>»

anonymous
()
Ответ на: комментарий от fmdw

Теперь любой полиморфизм будет считаться объектной моделью?

нет, наоборот: любая объектная модель — это одна из разновидностей полиморфизма. например, type class polimorfism в хаскеле — полиморфизм классов типов. то есть, метатипы как метаклассы в ооп.

кстати, ещё отличие ООП в Eiffel от других: «классы» ANY и NONE (ср. T и _|_ ).

обратно, скорее всего: non sequitur.

полиморфизм чего именно? полиморфизм наследования и аггрегации (Мейер вводит всего два отношения: быть потомком и быть клиентом, что-то вроде ассоциации в UML).

то есть: объектная модель — это способ реализации такого вот особого полиморфизма. полиморфизмы классов других типов — не объектные.

а наследование или посылка сообщений там — не суть важно, это реализация, а не принцип.

Боюсь, твой пост не укладывается в общепринятую терминологию.

может быть. дай своё общепринятое определение «объектная система».

по-моему, это а) базовые принципы ооп: наследование, инкапсуляция, полиморфизм наследования — или изоляция, посылка сообщений б) объектный полиморфизм в) реализация этих принципов в виде объектной модели.

anonymous
()
Ответ на: комментарий от anonymous

Официальная

Анонимус учится читать?

anonymous
()
Ответ на: комментарий от monk

MFC, OWL, Qt, и ещё полсотни других были друг с другом не совместимы
В то время как GObject (+GIR) действительно задаёт стандарт на все библиотеки, использующие его.

Какое-то упоротое сравнение. Если мы с тобой возьмёмся одновременно писать разные либы используя GObject, то «базовые типы», конечно будут одинаковые и совместимые (как собственно и в С++), но если у какого-то класса совпадёт имя и даже предназначение, то это всё равно будет два разных класса, как и в С++.

Я уж не говорю о том, что «фреймворки» обычно сложно друг с другом скрещиваются.

Ну а вообще иметь общий стандарт хорошо и ты сам про это говоришь. Да, он может быть не встроен в язык, но GObject как раз несколько громоздкий по сравнению с «встроенными» решениями.

DarkEld3r ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.