LINUX.ORG.RU

Функциональщина. Что выбрать?


0

0

Решил в свободное время заняться изучением модного нынче функционального программирования. Встал естественный вопрос: что выбрать? Этих всяких лиспов, хацкелей, оцамлей и т.п. вагон и маленькая тележка. Чтобы не распыляться выбрал Scheme, т.к. его используют в SICP, но настораживает его не слишком большая распространённость и «академичность». С другой стороны, лямбды и прочие «вкусности» потихоньку приходят и во всякие там питоны и даже плюсы. Не холивара окаянного ради, а сугубо для просвещения и развития спрашиваю: что изучать, чтобы не лежало оно потом мёртвым грузом? У каких языков какие плюсы, минусы и области применения?

★★★★

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

>>ок. Как же в хаскеле функцию сделать от переменного количества аргументов?

someFun:: [Inp] -> ResT

Какие проблемы то ? Нужно пропихивать произвольные типы с нужным контрактом? Для этого есть слово forall и экзистенциальные типы.

За протаскивание в функцию произвольного типа без контракта надо бить по рукам.

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

Из популярных языков - в Haskell && ML/Ocaml, наверно... В вами названном нормальной статической типизации нет.

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

>>Ведь система типов не даст внести какое-нибудь значительное изменение: не дай бог какая-нибудь часть программы станет на пару минут некорректной...

Лолчто?

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

если включить ворнинги, то на непокрытые паттерны происходит ругань. -Wall должен быть включён всегда. -Wall -Werror на финальном вылизывании.

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

> Цацкель, между прочим, тоже мелкософтом поддерживается. Ещё бы кто сказал - зачем...

Ну а зачем безруким слепым инвалидам на паперти подают?

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

Ну, статическая типизация без полиморфизма и вывода типов действительно скорее минус чем плюс, что попытки писать стеки да списки на сях и показывают.

Yep.

А полиморфизм без грамотного построения иерархии классов типов - это точно минус.

Nope. Иерархия получается, если у тебя ООП, а оно редко реально нужно.

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

> В вами названном нормальной статической типизации нет.

Т.е. я правильно понимаю, что от статической проверки типов в С++ пользы особой нет, и если бы мы сравнивали динамическую проверку типов с статической как в С++, то вы бы признали превосходство динамической. Но вот в Haskell есть несколько суперфич, которые поднимаю статическую проверку типов на совершенно новый уровень, которая намного, намного круче всего остального? Или как?

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

Вот как уже надоели эти споры о типизации!

Чтобы выработать свою точку зрения, нужно попробовать поработать и так, и этак. Я пробовал. Вывод такой:
В основном, статическая типизация полезна. Во-первых, программы работают быстрее. Во-вторых, в языках типа С++ и, особенно, Object Pascal, который мне нравится (и я этого не стыжусь), знание типа переменной позволяет делать код более компактным и легко читаемым.
Касаемо же ошибок - эта проблема преувеличена. Ошибок типов не так уж и много.

В некоторых случаях должна быть свобода использовать полиморфные типы и это должно быть действительно легко и удобно. Наилучшим образом эта свобода дана в лиспе. Лисп - это язык со строгой типизацией, мы можем писать совершенно полиморфный код, и в любой момент можем динамически узнать тип любого объекта. В Дельфи тоже сделано неплохо, благодаря наличию у подавляющего большинства классов общего предка - TOBject, ну и благодаря наличию variant open array parameters. В С++ такого нет, можно лишь пытаться эмулировать полиморфный вариант в каких-то частных случаях и придётся постоянно тратить на это какие-то силы не только на этапе определения, но и на этапе использования.

Вообще же, в динамически типизированном языке проектирование - это процесс как бы более линейный. Просто придумывать архитектуру - нужно всего лишь разбить функционал по модулям, а хранение - по типам данных. В случае лиспа функции не принадлежат типам, поэтому исчезает ещё одна обязанность: не нужно разбивать функционал по типам. Функция просто что-то делает с какими-то объектами, а не «воплощает какую-то активность данного объекта». Сказуемое идёт впереди подлежащего.

Может быть, это менее естественно, чем в С++, но, учитывая параноидальную политику ограничения доступа, принятую в С++ - это облегчает ситуацию. Элементы, из которых состоит мир, на самом деле нельзя разбить так, чтобы каждый элемент принадлежал кому-то одному. Жизнь - это как минимум, игра объектов, а элементы - это что-то общее между ними. Вчера территория государства была private, а сегодня на неё, не спросив авторизации, въехали чужие танки. И она стала private в другом экземпляре. Но есть ещё партизаны... Да и когда она была private, реально на ней действовало не государство как объект, а его граждане, которые тоже могли зарубить друг друга топором на меже. Соответственно, объектная модель вообще не является адекватным отражением мира. ООП - это болезнь. Попытка защитить то, что на самом деле не является собственностью защищающего, не подлежит защите и не может быть защищено, в совершенно неадекватных реальности терминах. Я не использую private вообще никогда. Ну, почти никогда. Только в тех случаях, если, например, у меня есть конструктор, а объект всегда должен создаваться только с помощью фабрики. Если мне нужно, чтобы пользователь не трогал какие-то данные, я пишу строчку комментария: «не трогай это, потому что...».

Хотя это я что-то не про то... С++ я привёл просто как пример, может быть, слишком многословно... Как пример извращённого сознания. Почему мне не нравится Хаскель? Потому что он тоже извращён и, хуже того, лицемерен изначально. Жизнь не является функционально чистым вычислением. Каждый шаг оставляет след (С). Функционально чист лишь процесс нанесения текста, при условии, что этот белый лист потом сразу отправляется в шрёдер, а сам процесс записи непрерывен по времени и никто посторонний не может прочитать через плечо. И даже в голове у пишущего не оказалось никаких побочных эффектов, т.е., он не сделал выводов из написанного и всё сразу забыл. По-моему, этот пишущий должен быть признанным недееспособным ввиду явного распада личности. В этом духе, все основные способы оставления следов, такие как запоминание (хеш-таблицы), чтение и запись файлов, в Хаскеле объявлены греховной деятельностью и они наказываются включением io и оборачиванием в какой-то неудобный синтаксис (оператор Do или как он там называется). Далее, в стиле двоемыслия, хаскелисты постигают трансцендентальность Монады и начинают думать, что всё равно, даже когда они читают файл, это действие функционально чисто. Монада отпускает этот грех. Т.е., Хаскель - это секта, болезнь сознания и извращение. Причём, оно присутствует в Хаскеле изначально и совершенно из него неустранимо. Я не люблю вот такую, крупную и тотальную ложь, сопровождающуюся искажением всей картины мира. Может быть, можно писать и на Хаскеле, но для этого нужно твёрдо помнить, что ты находишься в анти-мире, а вокруг тебя - зазомбированные сектанты. На самом деле, это тяжело и я не уверен, что оно того стоит.

Так вот, это - первичный недостаток Хаскеля. Вторичный - тоже идеологический. Он говорит о том, что Священный Проверщик Типов спасёт нас от ошибок. Бред, конечно. Но люди верят в это и пытаются отобразить свои идеи на систему типов так, чтобы Священный Проверщик Типов уделил им своё внимание. Я не знаю Хаскель совсем. В С++ такая болезнь тоже есть, хотя она продиктована больше соображениями производительности - там изгоняли злой дух динамизма и это было оправдано во многих случаях. В Хаскеле же это делается из чисто религиозных соображений. Независимо от системы типов, жизнь изменчива. Вчерашняя гусеница завтра родится бабочкой и это невозможно отобразить в статичной системе типов вообще никак. Поэтому, речь может идти только о воплощении в коде извращённой картины мира. Труд по извращению картины мира экспоненциально сложен, потому что мы не рисуем икону - мы пишем программу, которая должна дать полезный результат. Судя по некоторым постам на ЛОРе, в Хаскеле проблемы имеют другой характер, чем в С++, но общая идея та - же. Есть жизнь, есть прокрустово ложе Священного Проверщика Типов. И люди разбивают лоб в молитве, пытаясь сделать так, чтобы их мысли о жизни уложились в прокрустово ложе понимания божка. Люди, не пытайтесь насиловать жизнь, она сильнее вас и вы в итоге изнасилуете только себя!

Справедливости ради, мне не нравится и лисп, за его анти-синтаксис. Но это можно перетерпеть, потому что это порождает лишь линейную проблему и потому что есть макросы. Т.е., лисп обладает таким уникальным свойством, как _непринуждёность_ перевода мыслей в код. Остальные языки порождают экспоненциальные проблемы. Поэтому, на лиспе работать можно и нужно. Схема - это язык не особо серьёзный. Даже лучшая с точки зрения удобства реализация - Plt Scheme, явно написана не для промышленного применения, судя по слабым средствам отладки.

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

Отвечу я:

Т.е. я правильно понимаю, что от статической проверки типов в С++ пользы особой нет, и если бы мы сравнивали динамическую проверку типов с статической как в С++, то вы бы признали превосходство динамической.

Пожалуй, да.

Но вот в Haskell есть несколько суперфич, которые поднимаю статическую проверку типов на совершенно новый уровень, которая намного, намного круче всего остального?

Нет. В Haskell система типов устроена ОЧЕНЬ сильно иначе, это не C++-ная система с дополнительными фичами.

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

Ещё один приплюснутый...

Касаемо же ошибок - эта проблема преувеличена. Ошибок типов не так уж и много.

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

Наилучшим образом эта свобода дана в лиспе.

Нет.

учитывая параноидальную политику ограничения доступа, принятую в С++

Ха! Там «политика ограничения доступа» - это одна большая дыра.

Хотя это я что-то не про то...

Совершенно.

Жизнь не является функционально чистым вычислением.

И какая нафиг разница?

И даже в голове у пишущего не оказалось никаких побочных эффектов, т.е., он не сделал выводов из написанного и всё сразу забыл.

Ещё раз: Хаскель не хочет отсутствия сайд-эффектов, он хочет КОНТРОЛЯ за ними.

в какой-то неудобный синтаксис (оператор Do или как он там называется)

О, да, очень неудобно:

main =
   do putStr "What's your name? "
      name <- getLine
      putStrLn ("Hello, " + name)
Интересно, что тогда такое «удобный синтаксис»???

Монада отпускает этот грех.

По-моему, у тебя ПГМ.

Я не знаю Хаскель совсем.

Это видно, иначе не нёс бы подобный бред.

Давай ты попробуешь говорить о том, о чём имеешь хотя бы МИНИМАЛЬНОЕ представление. Иначе твою речь не получается воспринимать как-либо иначе, чем как пиздёжь.

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

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

Брр. У вас каша в голове. Да и «удобство» это такое странное необъективное понятие. Мне вон текст «удобнее» набирать в VIM (привычка). Теперь я имею право обливать помоями всех пользователей имакса?

Причём, оно присутствует в Хаскеле изначально и совершенно из него неустранимо.

В начале ввод/ввывод был сделан не через монады. Сюрприз?

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

> Вот нифига себе я спросил...

Да, это здесь больная тема:)

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

> Я не знаю Хаскель совсем.

А, понятно. Сейчас модно что-то критиковать, совсем не зная предмет? Ах да, это же лор. А говорят, что лор не тот!

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

>В начале ввод/ввывод был сделан не через монады. Сюрприз?

Так, для общего развития, а как был сделан? Желательно бы ссылку посмотреть подробнее. (у меня есть некоторые идеи, как можно было бы, но...)

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

> Сейчас модно что-то критиковать, совсем не зная предмет?

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

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

>> В начале ввод/ввывод был сделан не через монады. Сюрприз?

Так, для общего развития, а как был сделан?

Через жопу.

Желательно бы ссылку посмотреть подробнее

Ищи статью SPJ «Being lazy With Class»

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

>В опровержение этого твоего бреда утверждения я привел кусок кода, где типы языка существенно помогают проверять формальные критерии корректности программы.

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

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

> > Я не знаю Хаскель совсем.

Это видно, иначе не нёс бы подобный бред.

Да, первый аргумент сектанта-рекрутера. «Не приобщась к трансцендентному знанию, ты не можешь понять, как у нас хорошо». Далее ты идёшь приобщаться и тебе говорят «оставь своё я за порогом. Начальник всегда прав. Если не прав, см. пункт 1». Т.е., приобщиться, не лишившись своего я, никак невозможно. Я уже видел достаточно сект (в жизни, а не в программировании). Мне не нужно изучать глубины вашего учения, чтобы увидеть в нём искажения картины мира. Их видно с первого взгляда. Лучше скажи, есть ли на Хаскеле проект, подобный по масштабам ACL2 или Mathematica. Это будет для меня аргументом из реальной жизни, а не из сектоводства.

> в какой-то неудобный синтаксис (оператор Do или как он там называется)

О, да, очень неудобно:


Я опираюсь на мнение тех, кто знает Хаскель и дал о нём такие отзывы. Цитату не приведу - я вынес своё мнение о Хаскеле уже несколько лет назад и пока не вижу повода его поменять.

К слову, в Oracle тоже есть способ контролирования побочных эффектов. Это вообще не так уж и сложно. Код делится на две части: чистую и нечистую. Например, с помощью специальной директивы компилятора pure. Весь код представляется как набор функций, каждая функция состоит из вызовов других функций и таких действий, как связывание, ветвления и т.п. По любой функции легко вывести, является ли она чистой: она должна вызывать только чистые функции и не содержать деструктивных присвиваний к данным, которые переживут её вызов. Если функция декларирована чистой и не является чистой - то это ошибка компиляции. В остальном, кроме директивы компилятора, никаких отличий между чистым и грязным кодом быть не должно. В Хаскеле, как я понял, чистый и грязный код существенно отличаются по синтаксису.

Кроме того, если уж код грязен, то он не просто «грязен и всё». Он может быть грязен относительно каких-то одних вещей (например, заполнять глобальные хеш-таблицы), но при этом чист относительно внешней базы данных (т.е., не делать запросов на update или DDL).
Я весьма сомневаюсь, что в Хаскеле возможно отразить подобную чистоту так же естественно, как собственно чистоту вычисления. Потому что это вообще невозможно сделать в статике. Хранимая процедура в базе с одним и тем же именем могла вчера быть чистой, а сегодня стать грязной.

Ну и если подойти к более-менее реальным задачам. Когда-то я читал книжку по Прологу и быстро стало ясно, что хороший алгоритм обхода произвольного связного графа требует таскать с собой таблицу (хеш-таблицу!) всех узлов, в которых мы уже были. При этом, по сути, само вычисление является функционально чистым, т.к. хеш-таблица локальна по отошению к вычислению. В Прологе тех времён нельзя было иметь локальную хеш-таблицу. В лиспе, естественно, такой алгоритм пишется легко с помощью локальных функций и всё остаётся красиво и чисто функционально (хотя компилятор не может этого доказать). На тот момент, когда я составлял своё мнение о Хаскеле, там хеш-таблицы были в io. Всё. Я до сих пор не могу спокойно об этом думать, у меня внутри всё начинает кипеть и мне хочется отправить в штаб-квартиру хаскелистов даже не порошок сибирской язвы, а конкретную атомную бомбу. Ну или хотя бы вакуумную.

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

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

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

Я опираюсь на мнение тех, кто знает Хаскель и дал о нём такие отзывы.

Снова пиздёж.

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

Попробуй познакомиться с тем, на что пиздишь. Можно.

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

При чём тут твои грязные базы данных.

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

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

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

> 1,428 строк ... не устроит?

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

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

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

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

Конкретно на цацкеле статическая типизация, вывод типов и полиморфизм позволяет достаточно generic programming без макросов, т. е. средствами языка и без необходимости таскать словари функций руками. Получается очень компактно и достаточно читабельно, в отличии от.

Может быть тогда продемонстрируете семантически похожее на do из лиспа, вот что примерно нужно:

(do ((спецификация_1) (спецификация_2) ... (спецификация_n))
    ((условие_окончания) ф1 ф2 ... фn)
  произвольный_код)
спецификация_i это (var init inc)
init,inc,ф1...фn,условие_окончания - произвольные формы
var в спецификации - это переменная видимая в произвольный_код, значение которой вначале есть значение формы init, а каждую итерацию вычисляется inc. 
спецификации вычисляются параллельно, хотя в do* последовательно, пусть будет это несущественно.
Обобщенная декларативная итерация по произвольному числу аргументов.

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

> не желаете высказаться на тему системы типов в Haskell?

шикарная вещь :)

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

unC0Rr ★★★★★
()

что-то тут все притихло, вот вам мнение SPJ на тему динамика/статика.

Seibel: So that points out that there are programs that are correct,
because you’re assuming a legitimate source-to-source transformation,
which, if you had written it by hand, the compiler would have said, “I’m
sorry; I can’t type this.”


Peyton Jones: Right. That’s the nature of static type systems—and why
dynamic languages are still interesting and important. There are programs
you can write which can’t be typed by a particular type system but which
nevertheless don’t “go wrong” at runtime, which is the gold standard—
don’t segfault, don’t add integers to characters. They’re just fine.


Seibel: So when advocates of dynamic and static typing bicker the dynamic
folks say, “Well, there are lots of those programs—static typing gets in the
way of writing the program I want to write.” And then the fans of static
typing say, “No, they exist but in reality it’s not a problem.” What’s your
take on that?


Peyton Jones: It’s partly to do with simple familiarity. It’s very like me
saying I’ve not got a visceral feel for writing C++ programs. Or, you don’t
miss lazy evaluation because you’ve never had it whereas I’d miss it because
I’m going to use it a lot. Maybe dynamic typing is a bit like that. My feeling—
for what it’s worth, given that I’m biased culturally—is that large chunks of
programs can be perfectly well statically typed, particularly in these very rich
type systems. And where it’s possible, it’s very valuable for reasons that
have been extensively rehearsed.

But one that is less often rehearsed is maintenance. When you have a blob
of code that you wrote three years ago and you want to make a systemic
change to it—not just a little tweak to one procedure, but something that is
going to have pervasive effects—I find type systems are incredibly helpful.
This happens in our own compiler. I can make a change to GHC, to data
representations that pervade the compiler, and can be confident that I’ve
found all the places where they’re used. And I’d be very anxious about that
in a more dynamic language. I’d be anxious that I’d missed one and shipped a
compiler where somebody feeds in some data that I never had and it just
fell over something that I hadn’t consistently changed.

I suppose static types, for me, also perform part of my explanation of what
the program does. It’s a little language in which I can say something, but not
too much, about what this program does. People often ask, “What’s the
equivalent of UML diagrams for a functional language?” And I think the best
answer I’ve ever been able to come up with is, it’s the type system. When
an object-oriented programmer might draw some pictures, I’m sitting there
writing type signatures. They’re not diagrammatic, to be sure, but because
they are a formal language, they form a permanent part of the program text
and are statically checked against the code that I write. So they have all
sorts of good properties, too. It’s almost an architectural description of part
of what your program does.


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

продолжение


Seibel: So do you ever write a program that you know is correct but
somehow falls outside the bounds of the type checker?


Peyton Jones: This comes up when you’re doing generic programming,
where you want to write functions that will take data of any type and just
walk over it and serialize it, say. So that’s a time when types can be a bit
awkward and an untyped language is particularly straightforward. It couldn’t
be easier to write a serializer in an untyped language.

Now there’s a small cottage industry of people describing clever typed ways
of writing generic programs. I think such things are fascinating. But it’s
somehow just isn’t as simple as writing it in a dynamically typed language.
I’m trying to persuade John Hughes to write a paper for the Journal of
Functional Programming on why static typing is bad. Because I think it would
be very interesting to have a paper from John, who’s a mainstream, strongly
typed, very sophisticated functional programmer, who is now doing a lot of
work in untyped Erlang, saying why static types are bad. I think he would
write a very reflective and interesting paper. I don’t know quite where we’ll
end up.

I think I would still say, “Where static typing fits, do it every time because it
has just fantastic maintenance benefits.” It helps you think about your
program; it helps you write it, all that kind of stuff. But the fact that we keep
generating more and more sophisticated type systems is an indication that
we’re trying to keep pushing the boundary out to say more in the world—
to cover more programs. So the story hasn’t finished yet.

The dependently typed programming people would say, “Ultimately the type
system should be able to express absolutely anything.” But types are funny
things—types are like a very compact specification language. They say
something about the function but not so much that you can’t fit it in your
head at one time. So an important thing about a type is it’s kind of crisp. If it
goes on for two pages, then it stops conveying all the information it should.

I think the direction I’d like to see things go is to have still crisp and
compact types which are a little bit weak, precisely so that they can be
crisp, along with invariants, perhaps stated in a rather richer language than
the inferable type system, but which are still amenable to static checking.
Something I’m working on in another project is to try to do static
verification for pre- and post-conditions and data-type invariants.

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

> какой у вас опыт работы с динамической проверкой типов?

Javascript в браузере, для другого моего проекта (веб-приложение: сервер на хаскеле, AJAX, XML, YUI). Работал с ним немного, и прежде всего поражает разброд по поддержке различных вещей браузерами, правда это к делу не относится. Но в связи с этим неприятно возиться с undefined, not object и прочими вещами в рантайме, который не блещет поддержкой дебага и документированностью (хотя это, конечно, камень скорее в огород браузеров, а не динамических языков).

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

Может быть тогда продемонстрируете семантически похожее на do из лиспа,

Первый драфт, 29 строк:

{-# LANGUAGE Arrows, ExistentialQuantification #-}
module LispDo where
import Prelude hiding (id, (.))
import Control.Category
import Control.Arrow
import Control.Monad
data LispDo x y = forall state. LispDo state (x -> state -> (y, Maybe state))
runLispDo :: x -> LispDo x y -> y
runLispDo x (LispDo init body) = runLispDo' init where
    runLispDo' oldState =
        case body x oldState of
          (y, Nothing) -> y
          (_, Just newState) -> runLispDo' newState
loopVar :: a -> LispDo (a -> a) a
loopVar init = LispDo init (\f x -> (x, Just $ f x))
stopIf :: LispDo Bool ()
stopIf = LispDo () (\b () -> ((), if b then Nothing else Just ()))
instance Category LispDo where
    id = arr id
    LispDo init2 body2 . LispDo init1 body1 = LispDo (init1, init2) lispDoCompose
        where lispDoCompose x (oldState1, oldState2) =
                  let (y, mbNewState1) = body1 x oldState1
                      (z, mbNewState2) = body2 y oldState2
                  in (z, liftM2 (,) mbNewState1 mbNewState2)
instance Arrow LispDo where
    arr h = LispDo () (\x () -> (h x, Just ()))
    first (LispDo init body) = LispDo init lispDoFirst
        where lispDoFirst (x, z) oldState = let (y, mbNewState) = body x oldState in ((y, z), mbNewState)
instance ArrowChoice LispDo where
    left (LispDo init body) = LispDo init lispDoLeft
        where lispDoLeft (Left x) oldState = let (y, mbNewState) = body x oldState in (Left y, mbNewState)
              lispDoLeft (Right y) state = (Right y, Just state)
instance ArrowLoop LispDo where
    loop (LispDo init body) = LispDo init lispDoLoop
        where lispDoLoop x oldState = let ((y, z), mbNewState) = body (x, z) oldState in (y, mbNewState)
-- Testing:
evenLoop :: Integer -> LispDo () Integer
evenLoop n =
    proc () ->
        do k <- loopVar 0 -< (\k -> k + 2)
           stopIf -< k > n
           returnA -< k
testLoop :: LispDo () Integer
testLoop =
    proc () ->
        do k <- loopVar 0 -< (+ 1)
           m <- loopVar 1 -< (* 2)
           stopIf -< k > 10
           returnA -< m
Miguel ★★★★★
()
Ответ на: комментарий от Miguel

>> Ну, статическая типизация без полиморфизма и вывода типов действительно скорее минус чем плюс, что попытки писать стеки да списки на сях и показывают.

Yep.

Хочешь сравнить скорость петоновских стеков и нативных сишных? Или мосье из будущего, где вовсю в ходу QC и проблема производительности решена раз и навсегда?

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

> Какой сюрприз, SPJ предпочитает статическую типизацию :)

сюрприз в том, что он оказался не таким фанатичным, как некоторые здесь :).

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

Хочешь сравнить скорость петоновских стеков и нативных сишных?

Не хочу, о скорости речь вообще не шла.

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

> сюрприз в том, что он оказался не таким фанатичным, как некоторые здесь :).

Он просто вежливый. Вот это:

where it’s possible, it’s very valuable for reasons that

have been extensively rehearsed.

просто вежливая формулировка фразы «Общеизвестно, что статическая типизация рулит». А вот это:

I’m trying to persuade John Hughes to write a paper for the Journal of

Functional Programming on why static typing is bad. Because I think it would be very interesting to have a paper from John, who’s a mainstream, strongly typed, very sophisticated functional programmer, who is now doing a lot of work in untyped Erlang, saying why static types are bad.

вежливая формулировка «Да ХЗ зачем нужна эта динамическая типизация».

:)

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

> Хочешь сравнить скорость петоновских стеков и нативных сишных?

А ты хочешь сравнить? Я бы посмотрел на результат.

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

А что там у нас в хацкиле с отступами?

опционально

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

А что там у нас в хацкиле с отступами? Как в петоне?

Опционально. Можно и так, будет то же самое:

   main = do {
 putStr "What's your name? ";
          name <- getLine;
putStrLn ("Hello, " + name);
                    }

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

> Ты говно
Хех. Видать, задело за живое :) Я сам в армии не служил, но один сержант запаса мне рассказывал, что можно обсирать любыми словами строй, но нельзя вывести конкретного человека и обсирать лично его. Так что ты, пожалуй, перешёл границу допустимого. Я тоже, конечно, не подарок, но лично тебя я плохими словами не называл.

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

>>Иерархия получается, если у тебя ООП, а оно редко реально нужно. Эээ. Я криво сказал. Не развесистая иерархия, а аккуратное выделения классов типов и раскладка реальных типов по классам типов.

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

Первый драфт.

Забыл привести тест в REPL:

*LispDo> runLispDo () $ evenLoop 100
102
*LispDo> runLispDo () testLoop
2048

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

лично тебя я плохими словами не называл.

Кисо обиделося. У меня, зато, есть некоторые основания для утверждения «ты говно», а у тебя под твоим высером - ничего, как ты сам и признался.

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

> Он просто вежливый.

ну не везде, он еще там про то, что generic programming со статикой - попаболь, что иногда статика сложна и мешает программировать.

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

С тех пор как заимели долю более 0.5 процентов в проектах. Насколько мне известно, их доля таки более 0.5 процентов. В отличии от всякой эзотерики типа Coq. Хотя да, популярности php им в ближней перспективе не достичь...

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

>Не хочу, о скорости речь вообще не шла.

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

На всякий случай, довожу до твоего сведения, что хваленый гентушный portage нещадно тормозит на P IV 2.8 GHz. Написан на петоне, который все так обожают. Динамическая типизация, все дела.

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

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

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

Ещё раз, для таких, как ты: РЕЧЬ НЕ ШЛА. Не было сказано «это вообще неважно», не было сказано «это меня не волнует». Была констатация факта: в ДАННОМ обсуждении речь об этом не шла.

На всякий случай, довожу до твоего сведения

Неинтересно, извини.

Написан на петоне, который все так обожают.

Говори за себя.

Поделками на хацкиле не пользуюсь

Тогда твоё сраное мнение в данной дискуссии никому не интересно.

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

довожу до твоего сведения, что хваленый гентушный portage нещадно тормозит на P IV 2.8 GHz. Написан на петоне, который все так обожают. Динамическая типизация, все дела.

а у меня вот Firefox почему-то сильней тормозит; неужели тоже из-за типизации?

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