Здравствуйте, Паблик Морозов, Вы писали:
ПМ>Если речь идёт о верстке документов и использовании каких-то тулзов для конвертации их в различные форматы, то пусть хоть в ворде верстают, в этом ничего плохого нет. Просто из
ПМ>[quote] ПМ>Я лично ничего не верстаю вообще, как впрочем и GUI не рисую сам. Я больше занимаюсь проектирование архитектуры всего этого. И вот в рамках нашей архитектуры все html генерятся у нас с помощью xslt шаблонов из xml данных. ПМ>[/quote]
ПМ>Я сделал вывод, что речь идёт о каком-то веб-интерфейсе, где сервер генерируюет xml, который самописными xslt-шками конвертируется в веб-страницы. Такую придурь я встречал и именно с неё я . А если программисту не приходится трогать xml и xslt, то норм, не трогаешь — не пахнет.
На сайтах тоже всё через xslt (и как раз самописными), но всё в статике (а динамика вся через ajax) — даже не на сервере, а на компах разработчиков.
Т.е. в целом схема такая:
— пишущие текст люди имеют дело с текстом в спец. редакторах (геренирующих xml).
— программисты в теории (см ниже) занимаются только серверными (python) и клиентскими скриптами (jquery) и там обмен не через xml.
— дизайнеры делают шаблон для статики в xslt.
На практике программисты делают ещё перевод с "художественного языка" на xslt.
Плюс документация для сайта и в дистрибутив (chm) генерируется уже с помощью не самописных (docbook) xslt.
Здравствуйте, m e, Вы писали:
ME>>>скажем, почему список из объектов, у каждого из которых есть функция print, чем-то хуже "списка из print-ов"? V>>Тем что это объекты с ф-ей print, а не просто ф-ия print сама по себе. Больше сущностей.
ME>гы-гы
ME>а разве в хаскеле нет разницы между функцией и замыканием? афайк print легко может быть замыканием, и нет способа отличить замыкание от настоящей функции
Вот ты сам и ответил на свой вопрос -- отличить нельзя. Сущность с точки зрения программиста одна.
ME>а замыкание -- это тот же объект, только хуже оно так же как и объект, держит (т.е. не дает собрать мусорщику) данные, которые держат другие данные, и т.д.; при этом если про поля, захваченные замыканием, мы ничего не знаем, то поля объекта могут быть в явном виде ограничены, скажем, путем объявления класса final в java
Пиши на java, кто тебе не дает
ME>>>каким образом IO a -- чистая ф-я?
V>>Повторяю: V>>IO a = World -> (a, World)
ME>ммм... а мы про хаскель говорим или про что?
ME>
ME> data IO a = ... -- abstract
ME> instance Functor IO where
ME> fmap f x = x >>= (return . f)
ME> instance Monad IO where
ME> (>>=) = ...
ME> return = ...
ME> fail s = ioError (userError s)
ME>
ME>а "World -> (a, World)" это какие-то рассказы, которые могут и не соответствовать истине
ME>>а разве в хаскеле нет разницы между функцией и замыканием? афайк print легко может быть замыканием, и нет способа отличить замыкание от настоящей функции
V>Вот ты сам и ответил на свой вопрос -- отличить нельзя. Сущность с точки зрения программиста одна.
сущность одна с точки зрения *хаскеля*, но не программиста, которому надо еще и о ресурсах заботиться
так что уж не хаскелистам наезжать на объекты
V>Пиши на java, кто тебе не дает
что же касается настоящих функций, а не замыканий и не объектов, как членов массива -- этого в яве тоже нет, так что остается только с++11, где появилось слово final.
Здравствуйте, samius, Вы писали:
S>Здравствуйте, vshabanov, Вы писали:
V>>Здравствуйте, samius, Вы писали:
S>>>>>Ответь, дважды примененный результат getLine к одному и тому же миру даст одинаковый резльутат?
V>>>>Да S>>>Это учитывая текущую "реализацию" мира?
V>>Нет S>окей. Т.е. повторение результата где-то в голове, но текущая реализация мира этому не способствует. Спасаемся тем, что нам не позволяют юзать один мир дважды.
S>>>>>Если так, то функция World *printf(LPCSTR, World *) тоже становится формально чистой
V>>>>Да. S>>>Не согласен
V>>Ну что ж, ты конечно имеешь право на собственное мнение ) S>Да, иногда пользуюсь этим правом. S>Хотелось бы избежать любой напряженности, потому сделаю отступление в этом месте. S>Мнение мое сложилось отнюдь не в результате глубокого изучения вопроса или применения каких-то аналитических способностей. Просто в данный момент я так вижу и так понимаю. Право иметь собственное мнение немного для меня стоит без того что бы проверить это мнение а прочность путем столкнования с отличными от моего мнениями. Но в то же время, для меня это не спорт. Т.е. предпочту иметь более правильное, аргументированное мнение, чем свое собственное. S>Так же признаю за оппонентом право не способствовать мне в проверке прочности моего мнения и приму любую причину этого не делать, в том числе нежелание или отсутствие времени/возможности. А при наличии желания+возможности предлагаю в неспешном комфортном режиме навести ясность в этом вопросе (не исключаю, что и в моей голове).
V>>>>Т.е. в Си, добавив world к printf ничего не добъешься, т.к. язык не позволяет правильно ограничить его использование, а в хаскеле все чики-пики.
S>>>В хаскеле мы работаем чисто функционально не от того что мир нельзя подать дважды в один метод. А от того, что вручную не форсируем выполенение нечистых дейсвтвий, а лишь комбинируем нечистые действия чистым образом.
V>>Да да, конечно ) S>Отлично. Исходная точка найдена. Теперь надо выяснить, имеет ли способ ограничения повторного использования мира к определению чистоты. Имеет ли значение, как ограничивается повторное использование, будь это возможность компилятора, библиотеки, или честное слово в документации?
Если компилятор не бьет по рукам, то считай никакого ограничения нет.
V>>>>Но в программе мир моделируется тем самым World. S>>>Это не модель. Это затычка, dummy. S>>>При этом, как бы мир не моделировался в самой программе, программе все еще приходится взаимодействовать с миром вне программы. И любое такое взаимодействие нечисто по определению.
V>>Безусловно ) S>Рад, еще одна точка понимания. Дальше ход такой: имеет ли значение, как называется тип мира? Метафора, конечно важна. Но чисто формально наш мир мог бы называться Dummy, Foo, или Foo9278345987. И чисто формально уже не важно, какую связь с миром имеет этот параметр. Важно лишь то, что каким-то образом ограничена возможность повторного использования экземпляра.
Эмм, как называется тип вообще не имеет значения.
Мне что-то кажется, что ты никак не можешь отделить программу от ее выполнения. Вот смотри, возьмем мы какой-нить sin x. Чистая ф-ия. Но при ее вычислении процессор выполняет инструкции, грязно меняющие содержимое памяти, счетчик команд, кеши. Программа может прочесть что-нить из файла (если x получен из getContents, или из какого-нить memory mapped file-а), что-нить может отсвопиться, отвалиться по out of memory. Ну и проц может сгореть, в конце концов.
Т.е. даже sin, при сильном влезании в детали, очень нечистая ф-ия. Но все-таки, мы считаем ее чистой.
Также и с IO. В хаскелле нет нечистых ф-ий: не встроены в него переменные и взаимодействие с внешним миром. Однако работать с внешним миром все-таки надо. Чтобы не ломать чистоту стали считать мир обычным значением. Получается что какая-нить readLine :: World -> (String, World) обычная чистая хаскельная ф-ия, ведь она берет String не откуда-то а из аргумента. Т.е. глядя на тип такой ф-ии никак нельзя понять, что она не чистая (да и нет в хаскеле нечистых ф-ий).
Однако, в реальных программах тип World -- это все-таки не список строк stdin-а и stdout-а (хотя мог бы им быть в простых программах), а настоящий мир. А с реальным миром работать как с обычным хаскельным значением не получится. Мы не можем наплодить кучу миров и не можем использовать один и тот же мир дважды. Т.е. чтобы, при сохранении формальной чистоты, работать с реальным миром, а не заглушкой, необходимо, чтобы в любой момент времени в программе существовало только одно значение мира (тогда оно может меняться внутри, но программа этого все равно не заметит). Вот для того, чтобы значение было только одно, к нему не дают прямого доступа, только через bind/return/main.
Т.е. формально хаскелл полностью чистый язык. То, что writeFile что-то пишет на диск, программу на хаскеле не волнует никаким образом, для нее writeFile -- чистая ф-ия, преобразующая значение типа World. И, если ей подсунуть еще раз тот же мир (мысленно перенесясь назад во времени, например), то она выдаст тот же результат.
V>>>>Если она ничего кроме этого праметра больше не трогает, то стала. Но, т.к. параметр по-сути фиктивный и меняется реальный мир, то, чтобы сохранить чистую семантику, требуется чтобы этот параметр нельзя было использовать более одного раза. Тут то и вылезают монады с do-нотацией, которые позволяют это удобно сделать. S>>>Монады — лишь способ протащить мир по вычислениям. В printf можно было бы ограничить использование мира другим способом, например проверкой его счетчика использований и возвратом кода ошибки (или исключения в C++). Механизм ограничения числа использований параметра вообще не имеет никакого отношения к определению чистоты.
V>>Возврат ошибки/исключение на том же мире -- уже нечистая ф-ия. S>Согласен, формально это уже impure. Но, при стечении хороших обстоятельств, при правильном использовании, мы избежим кодов возврата, исключений и т.п. Тогда сможем говорить о некой относительной чистоте. Но на самом деле мы говорим о нечистоте вывода. Т.е. я убежден в том, что никакие средства, в том числе изменения компилятора, не позволят сделать ввод/вывод или взаимодействие с внешним миром относительно самой программы чистым.
Я выше попытался в очередной раз объяснить, как это возможно
V>>Покури unique types что-ли. Может так станет понятно про то, что при гарантии однократного использования параметра/результата сохраняется ссылочная прозрачность. S>Тут опять таки есть разные точки приложения ссылочной прозрачности. По определению ссылочная прозрачность выражения — это возможность заменить вычисление выражения результатом без изменения поведения программы. S>Важно понимать, что при замене функций ввода-вывода со внешним миром значениями, программа перестанет взаимодействовать с внешним миром. Внешнее поведение программы изменится. Потому, ни о какой ссылочной прозрачности в отношении внешнего поведения программы речи быть не может. S>О какой же тогда ссылочной прозрачности толкуют в uniqueness typing? ИМХО, они говорят о ссылочной прозрачности в отношении внутреннего поведения программы. Уникальные типы позволяют делать деструктивное обновление параметра в случае World->(a, World), и только лишь. Для внутренностей программы и только для них, все выглядит как будто бы мы получили новый экземпляр мира (пусть и на месте старого). Для внутренностей программы не имеет значения, вызывали ли мы взаимодействие со внешним миром, или просто получили вместо старого мира кортеж с новым миром. В этом отношении ссылочная прозрачность имеет место. Но как только мы вспоминаем о взаимодействии с внешним миром, оказывается что такая замена не является прозрачной.
S>Итого, uniqueness typing это лишь один из способов гарантировать невозможность повторного использования экземпляра с приятной особенностью, позволяющей делать замену по месту. Никакой чистоты при взаимодействии с внешним миром оно не обеспечивает.
А реальный мир постоянно меняется, вне зависимости от выполнения программы и мы можем спокойно "заменять по месту" значения мира на текущее
А>> MS Office как раз таки образец редкостного говнища. На кой он нужен, когда есть TeX, когда есть Mathematica (кстати, типичный пример архитектуры с оторванным от гуя ядром). A>Вообразим маленький эксперимент. Завхозу объяснили, как компьютер включать, и назначение некоторых клавиш. Бедолаге надо напечатать крупными буквами "Туалет закрыт из-за отсутствия воды". Есть возможность консультироваться по телефону (пока консультанту не надоест). Какой инструмент ему выбрать -- TeX или Word?
правильный ответ -- html, notepad и любой браузер
в ворде слишком легко запутаться, нажать не те кнопки, и потом х.з. сколько времени безуспешно пытаться объяснить консультанту, что случилось, а консультанту пытаться догадаться, как это исправить
ТеХ плох тем, что будет сыпать ошибками от незакрытых скобок
в блокноте достаточно написать "<html><h1>Туалет закрыт из-за отсутствия воды", сохранить как .htm, открыть в браузере, распечатать (и дальше ножницами обрезать, если не по центру)
ты-то сам ходил по своей ссылки? там четко написано "Portability : non-portable (GHC Extensions)", значит ты должен был ответить "мы говорим не о хаскеле, а о GHC Extensions" и не путать меня и окружающих
_>Xa. Я порадовался (может хоть здесь применение найдётся, вдруг чем-то удобнее scons'a будет да и вообще всё же статически типизированые языки больше люблю) и полез смотреть сразу.
и правда, хорошо бы сборочную систему на статически типизированном языке
K>Ага. Т.е. это еще веселее чем в анекдоте про нашедшиеся ложки и оставшийся осадок: тут ложки даже и не терялись, но есть мнение, что потеряются.
это неправильная аналогия
правильная будет такой: пришел MigMit и стал всем продавать нетеряющиеся ложки -- серебрянные на яве и шарпе, и золотые на хаскеле
я продемонстрировал, как теряются серебрянные ложки, и отсюда вывел *правдоподобное* заключение, что и золотые тоже могут потеряться
а вся тяжесть доказательства того, что ложки не теряются -- т.е. что скалярное произведение будет работать всегда -- лежит на MigMit, так как он опубликовал пост с этим утверждением, а вовсе не на мне (вспоминаем золотой чайник, летающий вокруг земли)
ME>>что значит "полноценность"?
K>В данном случае это означает, что код, который должен работать на языке с параметрическим полиморфизмом действительно работает.
он пыхтит, работает, и вообще очень старается, но вычисление скалярного произведия не гарантирует. супер!
ME>>объясни, в каком месте хаскель более декларативен, чем язык из ML семейства
K>В месте ссылочной прозрачности. И я не считаю, что "более декларативен" осмысленное словосочетание. Язык или декларативен или нет (императивен).
слово декларативность относится не только к комбинации "декларативен-императивен"
скажем, общепринято считать, что sql декларативен по той причине, что он описывает *что* надо селектировать, а не *как* это сделать; наличие update-ов не мешает ему считаться декларативным (и в update-ах можно пользоваться декларативными возможностями select-а)
именно поэтому я и употребляю словосочетание "более декларативен"
если же ты не согласен, и настаиваешь на своем, самобытном определении слова "декларативность", то пожалуста выпиши это определение полностью
_>Мне больше нравятся критерии, озвученные в SICP: нормальный порядок вычислений и декомпозиция на потоки. Т.о. к (чисто) функциональным языкам можно отнести Miranda, Clean и Haskell например.
_>>О, кстати, вспомнил ещё про yield в Питоне — тоже интересное решение для ленивости, в императивном стиле можно сказать. )))
V>Ну что уж поделать, коли генераторы через классы офигеешь писать.
интересует конкретный пример генератора, который неудобно пишется
V>Поинт в том, что в Хаскеле даже монада IO, которая кажется нечистой, также является чистой ф-ей. Просто у нее аргумент необычный ), но формально она чистая.
более интересно то, почему в ghc внезапно стали писать библиотеку, где IO a = IO (State# RealWorld -> (#State# RealWorld, a#)) ?
и кстати что тут означают решетки?
раньше вроде бы всем говорили "ребята, работа с RealWorld это удобное объяснение для начинающих, а на самом деле все сделано на continuations", и вот внезапно решили сделать монаду как в объяснении для начинающих? что случилось?
K>>В месте ссылочной прозрачности. И я не считаю, что "более декларативен" осмысленное словосочетание. Язык или декларативен или нет (императивен).
FR>Слово "декларативный" все-таки тут плохо подходит, у него слишком много значений, ты слишком сужаешь его смысл. FR>Ни к чему кроме терминологических споров это не приведет.
можно попытаться придумать ссылочнопрозрачный язык с каким-то дефектом, например который принципиально не позволит записать, скажем 7-tuples, а позволяет 2-tuples... или еще что-то в этом роде, что заставляет напрямую выписывать то, что можно было бы просто декларировать
FR>Хотя термин подобрать сложно, "аппликативный" вроде тоже не совсем подходит, остается только громоздкое "чисто функциональный".
ПМ> Разумеется, то, что функция возвращает одинаковые значения, ты тоже проверить не сможешь, т.к. не можешь создавать экземпляры или ссылки на *World. Но можно ли считать ли функцию чистой, если невозможно убедиться в обратном, это уже вопрос религии, а не математики.
че-то не вижу тут никакой религии
функция чистая при допущениях, которые мы сами добровольно собрались поддерживать, а вне этих допущений может творится черти-что, и что?