LINUX.ORG.RU

Чем так хороши макросы в Lisp?

 


4

7

Уже много всякого прочитал про лисп(в том числе Practical Common Lisp и уже даже освоился с Clojure), но никак не могу понять, чем же на самом деле являются макросы в этом языке. И этот вопрос не дает мне покоя т.к. лисп сильно повлиял на мое мышление и я вижу, что лисп (а особенно, common lisp для своего времени), действительно, лучше и удобней других языков (ну, за исключением странного скобочного синтаксиса ^^) ... Если бы его преимущества заключались в динамической типизации, сборке мусора и интерактивном цикле разработки, то их в полной мере имели бы питон, javascript и даже php.

Обычно пишут, что макросы - сильная сторона лиспа, которая отличает его от других языков и в качестве аргументов приводят неудачные примеры, которые довольно просто реализовать в других языках. Может кто-нибудь объяснить более-менее формально, что такое макросы? В чем их преимущества?

Для себя мне удалось выделить лишь два свойства макроса, отличающих его от функции:

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

Первое мне видится ограничением, которое приводит к целому ряду неудобств, как, например, невозможность применить apply к макросу(особено часто хочится сделать (apply and ...) или (reduce and ...)).

А второе может быть легко реализовано посредством функций высшего порядка хоть в C и C++. Для примера, в весьма популярной книге «Приемы объектно-ориентированного проектирования. Паттерны проектирования» Э. Гамма, Р. Хелм, Р. Джонсон, Д.Влиссидес описываются пaттерны Command и Interpreter - в комбинации это в точности макросы времени выполнения...



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

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

Т.е. ты так и не можешь объяснить, как написанный на Racket код работает на PS3?

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

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

Скипай бла-бла-бла до слайда, где сказано:

«Racket program that evaluated typed “Racket-ish” code that generates data usable by C++ runtime.»

Потом смотри на слайд «Architecture».

Их наговняканный поверх лишпика DSL используется тупо чтобы нашаблонить код на C++ и бинарные данные.

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

Их наговняканный поверх лишпика DSL используется тупо чтобы нашаблонить код на C++ и бинарные данные.

Все правильно, на таких DSL'ях и написаны геймплей, анимация, эффекты, звук и диалоги.

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

Все правильно, на таких DSL'ях и написаны геймплей, анимация, эффекты, звук и диалоги.

На этих DSLях написана генерация кода геймплея, анимации и т.д.

Ты еще скажи, что Linux написан на Make и M4.

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

Ты еще скажи, что Linux написан на Make и M4.

Не-не, он ща бомбанёт, что Linux написан на лишпе.

Потому что Си, Make и M4 — это частные случаи лиспа, лол.

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

Нет конечно, он написан на ассемблере, лол.

// до сих пор молчавший анонимус

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

На этих DSLях написана генерация кода геймплея, анимации и т.д.

Лол. Генерация откуда? С воздуха?

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

Last of Us глазами специалиста: Racket во время сборки интерпретирует скрипты, которые генерируют некоторые данные, впоследствии используюемые C++-рантаймом игры.
Last of Us глазами лиспера: ИГРА НАПИСАНА НА ЛИСПЕ!!!111

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

Генерация откуда? С воздуха?

Из шаблончиков, естественно.

Итак, ты признаешь хотя бы, что никакого лишпика в рантайме самой игры нет и быть не может?

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

Их наговняканный поверх лишпика DSL используется тупо чтобы нашаблонить код на C++ и бинарные данные.
«Racket program that evaluated typed “Racket-ish” code that generates data usable by C++ runtime.»

Да там по ходу только данные генерятся, даже никакой хваленой кодогенерации нет. Да и eDSL'ем не пахнет — просто скрипты на typed racket. Пшик, одним словом.

anonymous
()

Эй, вы чего? Нету там никаких шаблонов и DSL. Там есть просто скрипты на typed racket, которые во время бильда генерят некоторые бинари, вот и всё.

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

Ну так борщевики даже такой примитив словом «DSL» называют, чтоб чсв потешить.

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

О, и ты здесь, Бомбур. Добро пожаловать на огонёк.

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

Лиспер, одним словом.

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

Из шаблончиков, естественно.

Чушь. Если видео по ссылке не смотрел, читай пруф:

«In our Racket based system (DC), we develop a multitude of domain specific languages, a powerful gameplay scripting system, and systems for implementing animation, effects, and sound».

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

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

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

Ламка, по теме мысля появилась? Ты уже себе на три слива заработал.

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

«In our Racket based system (DC), we develop a multitude of domain specific languages, a powerful gameplay scripting system, and systems for implementing animation, effects, and sound».

Ну так тебе же уже разжевали сто раз, что это за такая «Racket based system». Что же ты такой тупой-то?

Бильд-скрипты на ракетке генерят ресурсы, которые потом подцепляет рантайм игры на С++. Всё. «Multitude of domain specific languages» — это лисповый баззворд, которым они обозвали рассыпуху скриптов.

Скажи, ты действительно настолько туп, чтобы и теперь утверждать, что «игра написана на лиспе»?

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

Они сами свои убогие шаблончики называют гордым словом «DSL», но сути-то это не меняет.

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

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

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

Какую предметную область описывает язык typed racket?

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

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

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

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

Бильд-скрипты на ракетке генерят ресурсы, которые потом подцепляет рантайм игры на С++. Всё. «Multitude of domain specific languages» — это лисповый баззворд, которым они обозвали рассыпуху скриптов.

Ну так давай пруф.

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

Ну так давай пруф.

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

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

Причем тут typed racket?

При том, что их мега-йоба-Racket-System устроена следующим образом (цитирую разработчика):

«Racket program that evaluated typed “Racket-ish” code that generates data

usable by C++ runtime.»

Таким образом, «язык предметной области» — это всего-навсего «typed Racket-ish code». Еще вопросы есть?

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

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

Лол, у гуманитарного мысля таки появилась?

Они в конце презентации там еще жаловались, что очень трудно заставлять экспертов писать на этом говне

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

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

Чушь.

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

Таким образом, «язык предметной области» — это всего-навсего «typed Racket-ish code». Еще вопросы есть?

Лол, ты тему читал, ламерок. Про макросы кому рассказывали три страницы?

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

а на с++ вот такое можно без извращений? Изменение кода программы во время ее выполнения. Остальным анонимусам хейтерам лиспа просто прочитать эти 2 статьи:

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

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

в самой игре нет ни строчки на лишпике

Дурак, расскажи нам, что же ты понимаешь под «игрой», и на чем же она все-таки написана? Повесели народ.

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

а на с++ вот такое можно без извращений? Изменение кода программы во время ее выполнения.

Смотря что называть «извращениями». Генерировать код на этапе исполнения и исполнять его можно.

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

Дети-дети...

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

В рантайме игры нет рантайма лиспа и нет кода, скомпилированного из лиспа. Там только код, сгенеренный скриптиками на лишпике. Если эта игра «написана на лиспе», тогда Linux написан на Make.

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

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

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

Остальным анонимусам хейтерам лиспа просто прочитать эти 2 статьи:

...и впервую очередь комментарии, заработавшие больше всего минусов. Наилучший показатель здравомыслия. Ведь на Швабре уровень маргинализации почти достиг ЛОРовского. Например, больше всего «плюсов» заработал следующий комментарий:

«Ибо воистину. Первый Язык, жемчужина посреди простых камней, и нет языков кроме Него. Скобки, в которых пустота — тело Его, мистическое двуединство кода и данных — дух Его, божественная рекурсия — сердце Его. Истинно говорю вам, избегающий света Его есть безумец, вот, свершается кара над главой его, и убогостью отмечены поделия его, подобные пустым глиняным горшкам рядом с хрустальным сосудом благодати Его. Принявший же и постигший истинный свет Его подобен прямой и отточенной стреле, чисты помыслы его и крепка рука его, и благословенны творения его, дарующие радость и утоляющие печали, ибо одухотворены духом Его и отмечены благодатью Его.»

И после этого кто-то будет утверждать, что лисп — не секта?

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

продолжать дальше дрочить на свои мейнстримовые яп

Я не дрочу на них, я их использую. ЧЯДНТ?

клепать безумно скучные проекты

Я работаю над безумно интересными проектами. ЧЯДНТ?

городить костыли

Мне не приходится городить костыли. ЧЯДНТ?

когда яп упрется в нетривиальную задачу

Мои ЯП не «упираются», когда на пути нетривиальная задача. Не могу понять, так что же я делаю не так?

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

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

Всё так, всё так, братух. Но есть одно «но».

Экскаваторы человечество использует, а лисп — нет.

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

Изменение кода программы во время ее выполнения.

А зачем? Не для того столько сил было вложено в разработку stack randomization, code pages protection, и тому подобных средств защиты кода, чтобы потом пришло какое-то борщехлебное чмо и оставило гигантскую дыру в безопасности.

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

Может, ты не ту специальность себе выбрал, если программирование тебе кажется скучным?

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

Я решаю только нетривиальные задачи. Тривиальные достаются моим подчиненным. И до сих пор я не встретил такой задачи, для которой мне был пришлось «городить костыли». Как раз тривиальные задачи это другое дело, там много однотипного boilerplate-кода, ну так у нас для этого дела препроцессоры есть и reflection. А в нетривиальных задачах сложность лежит совсем в иной плоскости, где никакие возможности языка эту самую сложность сократить не помогут. Каким бы борщехлебским язык ни был, а сложный алгоритм придумать он не поможет и не помешает.

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

«Скобочный» синтаксис - *одно* из основных преимуществ.

Вот всегда было любопытно, в каких ситуациях это - преимущество?

Полноценного интерактивного цикла разработки ни в одном из трёх нет. Есть только аналог REPL.

А чем REPL отличается от интерактивного цикла?

Я бы здесь первым примером Ruby назвал.

А что с Ruby не так? Оо

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

тогда отлаживайте в репле

Так в репле такой же убогий отладчик. Если в SBCL у меня всегда есть backtrace + inspect + выполнение произвольного кода в точке падения, то в racket всё приходится ловить руками.

Но лучше пишите юнит тесты.

Вот я именно про это. Нормального дебаггера нет, так как никому не нужно. Более того, читал чью-то статью, что дебаггер вреден, ибо провоцирует не писать нормальные тесты.

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

Я не про компиляцию. Я про ситуацию: разрабатываю что-то, через REPL создал тестовую ситуацию, а потом надо перезагрузить компьютер. В случае SBCL save-lisp-and-die, в случае Racket разве что гибернейт со всей операционкой или внешней утилитой останавливать и сохранять процесс (хорошо если один, а если несколько потоков?).

нету поддержки image-based разработки.

А как вы туда запихнете модули написанные на C/C++

Какая разница? Главное, чтобы всё состояние (переменные) в памяти лиспа было. Код можно и заново загрузить. По крайней мере я SBCL с биндингом к GTK сохранял в образ и заново загружал.

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

чтобы во время компиляции это разворачиовалось в вызовы Gtk.

В этом нет необходимости. Для GTK+ существует GtkBuilder.

Ну да. Лучше распаковывать при каждом запуске. В последнем 1С тоже так решили (формы сделали на XML). Теперь пользователи жалуются, что пока 1С каждую форму по разу не откроет, то тормозит жутко. Энтерпрайз, однако...

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

А можно на схеме так же легко написать подобие fexprs

#lang racket

(struct fthunk (f))

(define (feval x)
  (if (fthunk? x) ((fthunk-f x)) x))

(define (fand . args)
  (cond
    [(null? args) #t]
    [(feval (car args)) #t]
    [else (apply fand (cdr args))]))

(define (sum x y) (+ x y))
(define (sum2 x y) (+ (feval x) (feval y)))

(define (wrap f1 f2 f3 data)
  (map apply (list f1 f2 f3) (list data data data)))

(define lst '(1 2))

(print (wrap sum sum2 fand lst))

Пример использования fand

> (fand (fthunk (thunk (> 2 3))) 
        (fthunk (thunk (print "ok"))))
"ok"#t

> (fand (fthunk (thunk (< 2 3))) 
        (fthunk (thunk (print "no print"))))
#t

Можно (fthunk (thunk ...)) тоже в что-нибудь короткое переименовать

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

В рантайме игры нет рантайма лиспа и нет кода, скомпилированного из лиспа.

Ох, придется все-таки объяснять, а то так окажется, что «сама игра» написана на ассемблере или вообще в машинных кодах.

Итак, на чем написана The Last of Us, крутейшая игрушка года после GTA 5:

  • Геймплей, анимация, эффекты, звук и диалоги написаны на DSL'ях.
  • Компиляторы DSL'ей в низкоуровневый код игрового движка написаны на Лиспе.
  • Игровой движок написан на C++.

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

Говорилось именно про Лисп, так как изначально тема была про компиляторы DSL'ей, а не про сами DSL'и, движки, или, прости господи, рантаймы.

По-моему, понятно объяснил, даже гуманитарный анонимус поймет.

anonymous
()

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

Слив засчитан.

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

Обычный defmacro. А на советы академиков всем плевать.

А они его не юзали. Более того - по словам разработчиков даже ракетовская макросистема обладает некоторыми упущениями, общелисп же с его rain s-expr'ами вообще тут не котируется.

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