Форум программистов, компьютерный форум, киберфорум
Языки JVM
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.64/11: Рейтинг темы: голосов - 11, средняя оценка - 4.64
Заблокирован
1

Clojure Мультидиспетчеризация не по типам

15.03.2017, 22:48. Показов 2200. Ответов 26
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
что то я везде встречаю примеры мультидиспетчеризаци по типам. А как в лиспе диспетчеризовать не по типам, а по друзим вещам, по слотам, например?

Как будет выглядеть на лисповских мультиметодах аналог вот такого вот кода?
Код
A := Object clone do(
    a := 0
    accept := method(visitor, visitor doA(self))
)
B := Object clone do(
    b := 0
    accept := method(visitor, visitor doB(self))
)

Visitor := Object clone do(
   doA := method(acceptor, acceptor a = acceptor a + 1)
   doB := method(acceptor, acceptor b = acceptor b + 1)
)

a := A clone
b := B clone
visitor := Visitor clone

list(a, b) foreach(acceptor, acceptor accept(visitor)) 

writeln(a a, b b) #>>>>11
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
15.03.2017, 22:48
Ответы с готовыми решениями:

Мультидиспетчеризация и полиморфизм
Поскольку мультидиспетчеризация является частным случаем перегрузки -- перегрузкой в рантайме,...

Мультидиспетчеризация в Лиспе
Допустим, имеем иерархию Животное Млекопитающее Собака Кошка Земноводное...

Вопрос по типам
фрагмент файла unique_ptr.h: template <typename _Tp, typename _Tp_Deleter =...

вопрос по типам Си
всем доброго времени суток. вопрос будет про Си. я полный лох в этом. объясните мне,...

26
4527 / 3521 / 358
Регистрация: 12.03.2013
Сообщений: 6,038
16.03.2017, 18:54 21
Author24 — интернет-сервис помощи студентам
Цитата Сообщение от oopguru Посмотреть сообщение
нет
Сделайте другой объект по имени "spaceship", не копипастьте в него визитора из bar и покажите, что напечатает foo collide(qux). Если не "first object is asteroid", то нет никакой диспетчеризации по именам.

Цитата Сообщение от oopguru Посмотреть сообщение
не принимается.
Почему же? Вы конкретно для baz-а написали метод, я тоже. Всё честно.
0
Заблокирован
16.03.2017, 19:04  [ТС] 22
Цитата Сообщение от helter Посмотреть сообщение
Сделайте другой объект по имени "spaceship", не копипастьте в него визитора из bar и покажите, что напечатает foo collide(qux). Если не "first object is asteroid", то нет никакой диспетчеризации по именам.
он напечатает дефолтный визитор, который наследуеет от SpaсeObject. Это никакого отношения к делу вообще не имеет.
Цитата Сообщение от helter Посмотреть сообщение
Вы конкретно для baz-а написали метод, я тоже
В Io классы ничем не отличаются от объектов. Короче, не уводите тему в сторону. Диспетчеризуется все в зависимости от свойства name, никакой проверки на эквивалентность объектов там нет. Если вас так заели классы, то вот вам с классами код
Код
SpaceObject := Object clone do(
     name ::= nil
     collide := method(
       call evalArgs foreach(visitor, visitor  multyMethod(self))
     )
     multyMethod ::= method(spaceObject, writeln(spaceObject name ..  " collide with " .. self name)) // default 
)


Foo := SpaceObject clone setName("asteroid")
Bar := SpaceObject clone setName("spaceship")
Baz := SpaceObject clone setName("planet") setMultyMethod(
  method(spaceObject, writeln("just another behavor for " .. spaceObject name .. " with planet"))
)

foo := Foo clone
bar := Bar clone
baz := Baz clone


foo collide(bar, baz)
bar collide(foo, baz)
baz collide(foo, bar)



#>>>> asteroid collide with spaceship
#>>>> just another behavor for asteroid with planet
#>>>> spaceship collide with asteroid
#>>>> just another behavor for spaceship with planet
#>>>> planet collide with asteroid
#>>>> planet collide with spaceship
0
4527 / 3521 / 358
Регистрация: 12.03.2013
Сообщений: 6,038
16.03.2017, 19:13 23
Цитата Сообщение от oopguru Посмотреть сообщение
он напечатает дефолтный визитор, который наследуеет от SpaсeObject. Это никакого отношения к делу вообще не имеет.
А в чём тогда состоит смысл диспетчеризации по имени? Я думал, что для всех объектов по имени "spaceship" будет происходить что-то особенное. И вот вы создаёте объект по имени "spaceship", а он всего-навсего демонстрирует дефолтное поведение. Не ощущаю мощи.

Цитата Сообщение от oopguru Посмотреть сообщение
Диспетчеризуется все в зависимости от свойства name, никакой проверки на эквивалентность объектов там нет.
Вы сами пишете только что, что новый объект с именем spaceship демонстрирует дефолтное поведение. Значит, от имени не зависит, потому что foo collide(bar) и foo collide(qux) дают разный результат, хотя bar и qux имеют одинаковые имена. Более того, строчка "first object is ..." будет печататься, только если второй объект - bar. Выходит, всё-таки по объектам диспетчеризация.

Цитата Сообщение от oopguru Посмотреть сообщение
Короче, не уводите тему в сторону.
Я не понял, что я от чего увожу, но если я захочу пользоваться спецификатором eql, я буду. А то может ещё вам на "базисе лиспа" писать, как заходящим студентам?
1
Заблокирован
16.03.2017, 19:18  [ТС] 24
Цитата Сообщение от helter Посмотреть сообщение
будет происходить что-то особенное. И вот вы создаёте объект по имени "spaceship", а он всего-навсего демонстрирует дефолтное поведение. Не ощущаю мощи.
ну так в лисповской диспетчеризации тоже надо писать свой мультиметод на каждый случай, не? Если нет возможности сделать дефолтное пповедение, в случае отсутствия конфигурации, это только минус.

Цитата Сообщение от helter Посмотреть сообщение
если я захочу пользоваться спецификатором eql
В общем, лисп этого не может, я так и подумал. Только по типам.
0
4527 / 3521 / 358
Регистрация: 12.03.2013
Сообщений: 6,038
16.03.2017, 20:14 25
Цитата Сообщение от oopguru Посмотреть сообщение
ну так в лисповской диспетчеризации тоже надо писать свой мультиметод на каждый случай, не?
Я переписываю то, что вы мне даёте, без визиторов. И пока всё прекрасно работает без визиторов. Конечно, я не знаю тонкостей Io, я на ваш код смотрю как на псевдокод. Но если вас что-то не устраивает ― пишите словами. Не местоимениями. Пока вы пишете так: вываливаете псевдокод и говорите: «Сделайте то же самое, но не тоже самое». А потом: «Лисп ЭТО не умеет». А ЧТО сделать, и что ― ЭТО лисп неумеет ― неясно. Объясняйте русским языком. Мы же не гуру тут, нам ― русским языком.

Я примерно представляю, как сделать настоящую диспетчеризацию по именам, которой вы не продемонстрировали, без копипасты методов. Может, напишу.
0
Заблокирован
16.03.2017, 20:48  [ТС] 26
Цитата Сообщение от helter Посмотреть сообщение
Я примерно представляю, как сделать настоящую диспетчеризацию по именам,
меня интересует только вариант через мультиметоды
0
4527 / 3521 / 358
Регистрация: 12.03.2013
Сообщений: 6,038
16.03.2017, 21:16 27
Грубо говоря, если надо диспетчеризовать по имени, надо имя тоже сделать аргументом генеричной функции. Например,
Lisp
1
(defgeneric named-collide (who who-name with-whom with-whom-name))
Тут можно специализировать через (eql 'enterprise). (По техническим причинам имена будут символами, но это даже логично.) А (collide who with-whom) можно определить как (named-collide who (name who) with-whom (name with-whom)).
0
16.03.2017, 21:16
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
16.03.2017, 21:16
Помогаю со студенческими работами здесь

Помощь с примерами по типам ОС
Доброго времени суток. Есть классификация, по каждому пункту и подпункту из которой нужно привести...

Вопрос по типам данных
Ребят, помогите. Такой вопрос : Мне нужно сделать чтоб картинка по форме двигалась там по...

вопрос по синтаксису/типам
фрагмент файла unique_ptr.h: template <typename _Tp, typename _Tp_Deleter =...

неразбериха с типам VARCHAR
приветствую всем, мне возникла такая неразбериха с типам: VARCHAR вот ветом странице ...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
27
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru