T>Вы совсем не упомянули спарки (Control.Parallel par, pseq). Разве это не круто?
В теории — круто. На практике — полный отстой. В моей практике эти ваши стратегии и прочие pseq доблестно глючили (скажем, map обратабывал только несколько первых элементов списка, а весь хвост пропадал) и почти всегда были намного медленней чем элементарное линейное выполнение. И это несмотря на то, что вычисления должны были бы параллелиться легко и непринужденно.
Здравствуйте, Паблик Морозов, Вы писали:
ПМ>Здравствуйте, MigMit, Вы писали:
MM>>Разница в том, что в Хаскеле — нормальный ПП (с явной передачей словаря), а в плюсах — макросистема.
ПМ>Это особенность реализации. Готов поспорить на выпивку, что даже в стандарт не обязывает его реализовывать через передачу словаря (стандарт не читал :)
Здравствуйте, Rtveliashvili Denys, Вы писали:
RD>В моей практике эти ваши стратегии и прочие pseq доблестно глючили (скажем, map обратабывал только несколько первых элементов списка, а весь хвост пропадал)
Здравствуйте, alex_public, Вы писали:
_>идеальный функциональный язык, впитавшией в себя всё лучшее из всех остальных
К сожалению, хаскель не является идеальным ФЯ. Это сейчас единственный декларативный ФЯ, который можно назвать "реальным". Остальные либо мертвы, никогда и не жили, либо являются обычными императивными языками, на которые навешены пара-тройка функциональных фич. Последовательно писать функциональный код на таких языках либо вовсе не получается, либо такой код оказывается неприемлимо тормозным или вовсе не работающим. В такой ситуации у того, кто считает направление интересным просто нет выбора: хаскель как ФЯ безальтернативен, и уж какой есть — такой есть.
Утешает только то, что он сейчас прогрессирует заметными темпами и стал существенно лучше за довольно таки небольшое время.
Но я всерьез опасаюсь, что это не продлиться долго: хаскель становится популярнее, а популярность будет консервировать язык, его развитие замедлится, а потом и вовсе остановится. Скорее всего, задолго до того, как он приблизится к идеалу функционального языка.
... << RSDN@Home 1.2.0 alpha 4 rev. 1476>>
'You may call it "nonsense" if you like, but I'VE heard nonsense, compared with which that would be as sensible as a dictionary!' (c) Lewis Carroll
Судя по всему, ты написал на хаскеле дубовый императивный GUI-код, совершенно такой же, как на питоне. Вот по-этому разницы особой нет. Попробуй пописать что-нить более существенное, чем дергание сишных библиотечных ф-ий.
_>Т.к. об этом всё равно спросят, то напиши сразу: мои (и моих команд) основные инструменты в реальной работе это C++ (11-ый) и Python (2-ой). Естественно для всяких специальных целей применяются другие языки (всякие Javascript, Assembler, XSLT, Lua, SQL и т.п.). Кроме этого есть ещё набор языков, которые я (уже только лично) смотрел "для фана" (Lisp, Prolog, Smalltalk, OCaml, Erlang, D) и набор языков, которые когда-то изучал, но потом выкинул на помойку за ненадобностью (Pascal, Java, C#, PHP).
После lisp/prolog/ocaml с хаскеллом вообще особых сложностей быть не должно.
_>Haskell'я, как видно, тут нет — как-то так сложилось. А при этом я слышал о нём очень много всего от окружающих. Из этих слухов у меня сформировалось следующее впечатление: _>- язык мегасложный, только для самых самых, но зато кто освоит, может творить невероятные вещи, недоступные в других языках
Миф про мегасложность был распространен пару лет назад несколькими (одним?) крикливыми анонимусами. Про самых-самых и невероятные вещи -- видимо -- последствия этого мифа.
_>- язык находящийся на острие прогресса, так сказать идеальный функциональный язык, впитавшией в себя всё лучшее из всех остальных
На острие какая-нить agda. Haskell-у уже 20 лет, хотя он не потерял гибкость и развивается. Хаскелл -- такой исследовательский проект коммерческого качества.
_>- т.к. поддерживается статическая типизация, компиляция в native и были слухи о хорошем быстродействие в некоторых случаях, то я уже даже подумывал что это возможная замена наших реальных инструментов (хотя пока только D рассматривал в этом смысле).
А что у вас за задачи, что требуется быстродействие и при этом используется питон?
_>И вот у меня нашлось свободное время, когда я решился взяться за Haskell. Прочитал несколько вводных статей, скачал среду, написал несколько программок. Одну даже с GUI (на базе знакомой C++ библиотечки, к которой у Haskell есть биндинг) ради смеха. И захотел поделиться с вами ощущениями...
_>Если очень кратко, то "я в шоке".
Бывает )
_>А теперь подробнее... Для начала скажу что ничего сложного в нём так и не обнаружил — довольно простой и логичный язык. И это будет единственный положительный отзыв...
_>Ну а далее я просто увидел набор всех тех же самых вещей из своих рабочих языков (даже не из тех модных, которые "для фана"!), только записаных более неудобным (хотя и более кратким) способом. Те же генераторы, условия, шаблоны, только под другими названиями и с синтаксисом значками, а не словами. Разве что прямого аналога сечений и сопоставления с образцом вроде нет. Но сечение — это довольно редкая потребность на практике, которая к тому же вполне реализуема через что-то типа функтора. Ну а сопоставление с образцом оказалось совсем слабым (по сравнению с Прологом) — не намного сильнее какого-нибудь if/else...
"генераторы, условия, шаблоны" -- это что?
Сопоставление с образцом конечно слабее унификации (но мощнее серии if/then/else). Только вот в хаскеле можно проверить полноту сопоставления (и вообще правильность типов), а в прологе нет. Также со всякими ViewPatterns/PatternGuards/RecordWildcards сопоставление с образцом уже не кажется таким слабым.
Сечения используются довольно часто. Ты попробуй попиши код с ф-иями высшего порядка и поймешь.
_>И это я ещё не говорил про монады! Тут же наверное все знают что в Haskell по сути два отдельных языка. Он сам и ещё один встроеный, жутко кривой, по сути императивный язык для всего системного. В начале мне подобная идея показалась интересной — отделим весь "сомнительный" код от внутренней логики и т.п... Но когда я посмотрел (в примерах программ с GUI) к чему это приводит на практике... Ну вы наверное сами догадались, да? Вся программа — это одна "мегамонада". А самого "красивого" Хаскеля по сути вообще нет — только кривой код. А нафига тогда это вообще надо? Уж проще на Питоне, где и императивный и функционаьный код записываются в едином удобном стиле. И кстати монады огорчили ещё кое-чем. Зная что Хаскель компилируется в native, я надеялся что возможно будет путь для прямого вызова API OS. И он действительно по сути есть, но опять же только в этой кривой пародии на императивный язык. Конечно я понимаю что по другому и нельзя было (если хотим сохранять "чистоту"), но я надеялся на некое чудо. )))
Монады -- не встроенный язык. Это type class с небольшим сахаром для одной ф-ии. И служат они не только для IO. Хотя в дубовом IO (последовательный вызов библиотечных ф-ий) без использования ФВП и прочих хаскельныйх фишек могут выглядеть даже похуже питона. Только такой код на хаскеле почти не пишется (если только в примерах работы с GUI библиотеками .
foreign вызовы, если они чистые, могут быть и не в монаде. FFI у хаскелла вообще один из лучших, что я видел.
А пример записи императивного и функционального кода в питоне в едином стиле можно? В питоне вообще expression и statement -- разные вещи.
Более того, монада тоже чисто функциональная.
do x <- y; z -- это то же самое что y >>= \ x -> z
_>Есть ещё конечно действительно особая вещь — ленивость. Но сценарии её использования действительно интересны лишь на различных абстракциях (типа бесконечных структур данных), а в остальных случаях неленивые решения ничем не уступают. В общем саму возможность ленивых вычислений на уровне языка безусловно записываем в плюс, но она даже близко не окупает остальные минусы языка.
Ага, а еще ленивые вычисление позволяют тебе писать код в любом порядке, как удобно, а не как будет вычисляться. Т.е. если ты написал x = y where y = x, ты уже используешь ленивые вычисления.
А еще в хаскеле есть type classes/type functions/GADTs и еще куча плюшек, которых почти нигде больше нет.
_>В общем в итоге всего этого Haskell сполз для меня с мифического пьедестала (да, каюсь, это я сам воздвиг его, но в основном на основе окружающих слухов) супер языка и превратился в неудобную экспериментальную поделку... Теперь даже и не знаю где искать новую "серебряную пулю" для фана. Ну а о замене основных инструментов похоже пока даже и речи нет...
Для GUI посмотри на Tcl/Tk. Удобнее вроде пока ничего не придумали (правда выглядит плохо, но все равно стоит ознакомиться). Ну и попробуй напиши какую-нить логику к твоему GUI, может мнение о хаскелле поменяется )
Здравствуйте, MigMit, Вы писали:
MM>Здравствуйте, Паблик Морозов, Вы писали:
ПМ>>Здравствуйте, MigMit, Вы писали:
MM>>>1) Шаблоны — если имеются в виду шаблоны C++, то ничего близкого в Хаскеле нет.
ПМ>>Не вижу существенной разницы. http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.78.2151. ИМХО разница в основном в синтаксисе и в том, что на шаблонах скорее всего не сделать что-нибудь вроде (a ~ b) => ... То как это внутри реализовано — так вообще детали и в хаскеле более менделенная реализация, хотя можно было бы сделать и быструю как в крестах (путём запрета раздельной компиляции и увеличения кол-ва сгенерированного кода).
MM>Разница в том, что в Хаскеле — нормальный ПП (с явной передачей словаря), а в плюсах — макросистема.
А что такое ПП? И, чтоб 2 раза не вставать уже — что такое "(a ~ b) => ..."?
Интересно потестить возможности плюсовых шаблонов.
_> Разве что прямого аналога сечений и сопоставления с образцом вроде нет.
про какие сечения идет речь? (АОР?)
вообще единственное что в хаскеле хорошее -- это тайпклассы (ну и может по мелочам паттерн матчинг и может какие расширения, но я их не знаю)
крики про мега-крутой язык, как всегда, сильно преувеличены
полезность ФП проявится в основном при написании thread-safe кусочков кода (и да, там, если припрет, *придется* повторять весь этот хаскельный выпендреж в стиле эмуляции double linked list и прочих извращений) -- а вся остальная программа, как и раньше, будет императивная
короче, знание ФП потребуется почти лишь только тем, кто будет писать потокобезопасные структуры данных, да и то, возможно там будет использоваться вовсе не ФП, а доказательствами того, что императивные по сути действия снаружи выглядят одинаков независимо от того, как спланировались нити и как данные раскидались по кэшам процессоров, памяти и т.д.
Здравствуйте, graninas, Вы писали:
G>Ну что вам сказать... Вы не правы, потому что судите о Хаскеле исключительно с высоты своего опыта программирования на нем. И ваш опыт чрезмерно мал, чтобы ваша оценка была объективной и слишком эмоциональной...
Эх, я же специально привёл список знакомых мне языков, что бы было ясно что я вполне в курсе функционального стиля.
G>Ничего подобного. при правильном подходе к проектированию программы, любая монада прекрасно вписывается в остальной код и неотличима от него, потому как там все логично. Даже так напугавшая вас монада IO органично может быть частью чего-то большего. Просто смотрите достойные примеры, а изучение Haskell лучше начинать не с монад, а с принципов чистого функционального программирования. И тогда вы поймете, как разделить код на слои, чтобы не было одной мегамонады.
Речь не о том. Я имел в виду, что когда я заглянул в реальные примеры кода (не своего), то увидел что там кода "внутри монад" больше по объёму чем вне их. Соответственно возникает вопрос: "а нафига тогда так отделять было?". Ведь цена такого отдельния тоже есть — не слишком удобный синтаксис внутри монад.
G>О каких таких генераторах, шаблонах и условиях "с синтаксисом значками" идет речь? Вообще, тут в контексте беседы стоит упомянуть APL, и на том холиварную тему закрыть. (Но в скобках замечу, что ничто не мешает в Haskell делать синтаксис как со значками, так и словами. Зависит от предпочтений программиста.)
Генераторы это [ f x | x <- xs ]
В Питоне записываем как что-то типа [f(x) for x in xs]
Ну и дальше там есть аналоги буквальные на guards и так далее.
G>Это заявление вообще является показателем, что вам не известны все возможности сопоставления с образцом.
Хыхы, а вам известны все возможности сопоставления с образцом в Прологе? )
G>как и все сообщение, является лишь вашим желанием похоливарить, ибо Haskell тут ни при чем. А при чем — исключительно руки, которые и пишут код.
Ну пока что я разглядывал чужой код на Haskell в основном, а не свой. )))
Здравствуйте, alex_public, Вы писали:
_>Эх, я же специально привёл список знакомых мне языков, что бы было ясно что я вполне в курсе функционального стиля.
Для справки, в вашем списке языков примерно 0 наименований, которые подготовили бы вас к реальному функциональному стилю в котором пишут на хаскеле и примерно 12 наименований, которые бы затруднили понимание и написание кода на хаскеле. Именно это и имеют в виду, когда говорят, что хаскель "сложный": привычные по другим языкам "очевидные" умолчания и практики на пользу не пойдут.
... << RSDN@Home 1.2.0 alpha 4 rev. 1476>>
'You may call it "nonsense" if you like, but I'VE heard nonsense, compared with which that would be as sensible as a dictionary!' (c) Lewis Carroll
Здравствуйте, MigMit, Вы писали:
_>>Те же генераторы, условия, шаблоны,
MM>А нельзя поподробнее? Потому что пока я понимаю так: MM> ... MM>Я вполне допускаю, что понял неправильно, и прошу пояснить.
Я ответил в сообщение выше. Речь была про работу со списками.
MM>Это сомнительное утверждение. Единственное преимущество Пролога в этом смысле (ЕМНИМЭ) — это возможность использовать две одинаковых переменных (что-нибудь вроде [X|X|R]). В Хаскеле это эмулируется как (x : x' : rest) | x' == x. Причина этому — то, что в прологе любые термы можно сравнить на равенство; в Хаскеле нельзя. Это, в свою очередь, следствие того, что в Хаскеле терм может оказаться, например, функцией — а функции ну никак не сравниваются. Поэтому Хаскель не предполагает по умолчанию, что к переменным паттерна применимо свойство "такой же, как этот".
А как на счёт техники отката и отсечения из Пролога в сопоставление с образцом в Haskell?
MM>Это неверно. Монады — всего лишь один из множества полезных классов Хаскеля. Отличаются они только тем, что для них предусмотрен лёгкий синтаксический сахар. Но пользоваться им необязательно.
Эээ, я могу вызывать какие-то системные функции не из монад? Возможно я в чём-то не разобрался конечно...
MM>Ну, если вся программа — только лишь GUI, то удивляться нечему. А в "примерах", скорее всего, так и есть. Это то самое "отделение сомнительной части от внутренней логики", только в учебных примерах по GUI-библиотекам внутренней логики, собственно, нет.
Да, но у нас же не только GUI идёт в монадах, но и любые "внешние операции". Т.е. там в файл записать и по сети передать и так далее. Если мы вычтем и gui и всю эту непосредственную работу, то что остаётся то? Несколько алгоритмических кусков и всё? Я к тому что получается что код внутри монад будет очень сильно преобладать по объёму в любом реальном приложение...
_>>Но сценарии её использования действительно интересны лишь на различных абстракциях (типа бесконечных структур данных), а в остальных случаях неленивые решения ничем не уступают.
MM>Это тоже не так. На самом деле, практически во всех энергичных (== во всех остальных) языках есть элементы ленивости — потому что без них никак. Как минимум, конструкция if...then...else является ленивой вообще везде. Операторы "и" и "или" практически везде тоже ленивы — не вычисляют второй аргумент, если первого достаточно. А, скажем, нормальный Y-комбинатор вообще в энергичных языках не встречается, да и не может.
Само собой что ленивость можно реализовать в любом языке. Тут основное преимущество что она полноценно встроена в синтаксис языка. Но опять же на таком уровне она и нужна не так что бы часто. Т.е. я вспоминая свои проекты не вижу особо где она могла бы добавить реальных преимуществ.
Здравствуйте, Аноним, Вы писали:
А> Спрашивается — а на кой хрен вообще программировать GUI на Хаскелле? Да еще используя биндинги к чужеродным библиотекам, а не родную для Хаскелля идеологию functional reactive programming? Для GUI есть всякие там Tcl/Tk, идеально под эту задачу заточенные.
Я оценивал как язык справляется с этой задачей — он же позиционируется как универсальный... Да, и в данный момент у меня не стоит проблема выбора инструментария. Я просто присматривался не сможет ли вдруг Хаскель оказаться лучше моего текущего выбора. Оказалось что не может.
Да, и кстати дело не в GUI. Как я понимаю вообще вся внешняя работа (включая запись в файл) вынесена в монады. Соответственно инструмент получается неудобный почти для всех практических задач.
А> Функциональный код на Питоне?!? Не смешите мои панталоны! Какой такой "функциональный" код на языке, где expression и statement это разные вещи?
Там естествено нет "доказанной чистоты". ))) Но зато отлично сочетаются чисто функциональные практики с прямыми вызовами API.
А> Человеку, программирующему гуйню, ничего сложнее Tcl и не нужно по определению. Меня, честно говоря, сильно удивляет, как это жирный и сложный C++ (он на порядок сложнее того же Хаскелля) оказался в списке ваших инструментов. Не гуйнячий же язык, совсем не гуйнячий.
А мы как бы и не только GUI создаём — это только небольшая, но необходимая часть любого проекта. )))
Здравствуйте, vshabanov, Вы писали:
V>Судя по всему, ты написал на хаскеле дубовый императивный GUI-код, совершенно такой же, как на питоне. Вот по-этому разницы особой нет. Попробуй пописать что-нить более существенное, чем дергание сишных библиотечных ф-ий.
Нуу GUI в виде "мегамонады" — это я в основном не сам писал, а посмотрел примеры к библиотечке. А сам я писал естественно вообще без этого. Так, всякия математические фокусы попроверял ради интереса. Единственно что действительно "цепляет" — это ленивость встроенная в язык, а не путём "eval". Кажется в Maple такое было ещё помнится... Но неабстрактные практические применения что-то так и не пришли в голову.
V>А что у вас за задачи, что требуется быстродействие и при этом используется питон?
Питон используем во всех внутренних утилитах/процессах и для серверных скриптов на сайтах.
V>"генераторы, условия, шаблоны" -- это что?
Хы, уже 3-ий кто спрашивает. ))) Я там чуть выше ответил кому-то.
V>Сопоставление с образцом конечно слабее унификации (но мощнее серии if/then/else). Только вот в хаскеле можно проверить полноту сопоставления (и вообще правильность типов), а в прологе нет. Также со всякими ViewPatterns/PatternGuards/RecordWildcards сопоставление с образцом уже не кажется таким слабым.
Согласен) Я так и сказал что слабее прологовского и немного сильнее if/else. Просто я как бы ждал от языка слишком многого. Т.е. если сопоставление с образцом, то тогда уж уровня Пролога. Это же "великий хаскель". )))
V>Сечения используются довольно часто. Ты попробуй попиши код с ф-иями высшего порядка и поймешь.
Нуу функторы делают тоже самое в любом языке (где можно оперировать функциями). Тут просто это красивее и естественнее. Но как бы я не особо часто пользуюсь функторами в таком стиле.
V>Монады -- не встроенный язык. Это type class с небольшим сахаром для одной ф-ии. И служат они не только для IO. Хотя в дубовом IO (последовательный вызов библиотечных ф-ий) без использования ФВП и прочих хаскельныйх фишек могут выглядеть даже похуже питона. Только такой код на хаскеле почти не пишется (если только в примерах работы с GUI библиотеками .
Как бы не только GUI же получается но и любые "внешние операции"... Т.е. их получается "слишком много" в реальные приложениях. Я посмотрел там всякие примеры не образцового математического кода, а чего-то реального...
V>А пример записи императивного и функционального кода в питоне в едином стиле можно? В питоне вообще expression и statement -- разные вещи.
Нуу грубо говоря мы можем записать в генератор (или в map) чтение/запись в файл и никаких проблем не будет. Естественно это будет не "чистая" операция. Но мы же стремимся не к идеалу какому-то абстрактному, а к решению реальных задач. А "чистота" нам полезна только для удобства разработки, для уменьшения ошибок.
V>Ага, а еще ленивые вычисление позволяют тебе писать код в любом порядке, как удобно, а не как будет вычисляться. Т.е. если ты написал x = y where y = x, ты уже используешь ленивые вычисления.
Ага, удобно для символической математике. В Maple помнится тоже были всякие удобные вещи из этой области. Но я как бы математическим софтом не занимаюсь, поэтому на практике пока не особо вижу пользу.
V>Для GUI посмотри на Tcl/Tk. Удобнее вроде пока ничего не придумали (правда выглядит плохо, но все равно стоит ознакомиться). Ну и попробуй напиши какую-нить логику к твоему GUI, может мнение о хаскелле поменяется )
Эээ, это тут оффтопик конечно. Но Tcl/Tk — это недоинструмент по сравнению с современными мощными библиотеками с визуальными редакторами, нативными контролами и т.д. Да ну и главное: GUI — это как бы не главная цель, а просто один из обязательных параметров.
Что касается Хаскеля, то как бы я на самом деле не говорю что это плохой язык. Просто не такой хороший, как я о нём когда-то думал. Ну и как бы неполезный на практике в большинстве случаев.
Здравствуйте, m e, Вы писали:
ME>про какие сечения идет речь? (АОР?)
Которое "частичное применение"...
ME>полезность ФП проявится в основном при написании thread-safe кусочков кода (и да, там, если припрет, *придется* повторять весь этот хаскельный выпендреж в стиле эмуляции double linked list и прочих извращений) -- а вся остальная программа, как и раньше, будет императивная
Ага, вроде за счёт этого Эрланг сейчас процветать начинает.
Правда у меня на C++ с многопоточностью ни малейших проблем нет. Кстати, а вот в Питоне проблема с этим вроде имеется, но мы его не используем для таких задач.
Здравствуйте, Klapaucius, Вы писали:
K>Для справки, в вашем списке языков примерно 0 наименований, которые подготовили бы вас к реальному функциональному стилю в котором пишут на хаскеле и примерно 12 наименований, которые бы затруднили понимание и написание кода на хаскеле. Именно это и имеют в виду, когда говорят, что хаскель "сложный": привычные по другим языкам "очевидные" умолчания и практики на пользу не пойдут.