LINUX.ORG.RU

Джентельменский набор ЯП


1

0

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

А вообще какие языки и в какой последовательности было бы неплохо поучить?


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

> Правильно, только время вызова определено: при выходе из функции, в локальных переменных которой живёт рассматриваемая ссылка

Кем и где?

> А порядок удаления объектов соответствует их связям

Чему? O_o В RAAI порядок удаления определяется порядком объявления.

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

Да юзай что угодно, только не называй это RAAI.

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

А какой-нибудь with у вас есть? Заwithенные объекты будут грохаться по выходу из lexical scope в порядке fifo. Это можно считать RAII?

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

> какой-нибудь with у вас есть?

Ну ты же знаешь, что есть. Не во всех версиях, правда.

> Заwithенные объекты будут грохаться по выходу из lexical scope в порядке fifo. Это можно считать RAII?

Нет. Это такой finally на стероидах. RAAI основывается на вызове конструкторов и деструкторов в строго определенном порядке. Это есть только в Си++ (насколько я знаю).

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

> RAAI основывается на вызове конструкторов и деструкторов в строго определенном порядке. Это есть только в Си++ (насколько я знаю).

Педивикия про RAII: "ensures that when resources are acquired they are properly released by tying them to the lifespan of suitable objects: resources are acquired during the initialization of objects, when there is no chance of using them before the resource is available, and released with the destruction of the same objects, which is guaranteed to take place even in case of errors."

Смотрим на питон: конструктор есть, деструктор тоже, вызывается гарантированно в вполне определённый момент. Про порядок в определении ничего не сказано, да и здравый смысл подсказывает, что бог с ним, с порядком. Пусть в C++ он есть, но это ж не значит, что в RAII без него никак. Я всё-таки жду плохой для питона пример.

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

> Педивикия про RAII

В ланном случае педивикия не катит ни разу.

> вызывается гарантированно в вполне определённый момент

Пруфлинк или GTFO.

> Про порядок в определении ничего не сказано, да и здравый смысл подсказывает, что бог с ним, с порядком.

Это всего лишь _твой_ здравый смысл :D

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

>> Нет. Это такой finally на стероидах. RAAI основывается на вызове конструкторов и деструкторов в строго определенном порядке. Это есть только в Си++ (насколько я знаю).

Потому, что только в С++ есть деструкторы (ну почти только в нем :)). А ту же самую концепцию - автоматическое освобождение ресурсов при выходе из области видимости можно реализовать не только в конструкторах/деструкторах. Тот же with-open-file, если такие вызовы вложить друг в друга закроет ресурсы в порядке обратном их созданию при выходе ссылок на ресурсы их лексической области видимости. Так почем же это не RAII?

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

> Тот же with-open-file, если такие вызовы вложить друг в друга закроет ресурсы в порядке обратном их созданию при выходе ссылок на ресурсы их лексической области видимости. Так почем же это не RAII?

Потому что в нем конструкторов нет, блин. Ты лучше скажи, чем это не finally?

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

>> Потому что в нем конструкторов нет, блин.

Дык для реализации RAII коснтрукторы/деструкторы особо не нужны, вот в чем фишка.

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

> Дык для реализации RAII коснтрукторы/деструкторы особо не нужны, вот в чем фишка.

Я спросил, на что больше похожи with-блоки - на finally или на RAII в понимании Си++. Ты ответишь? Еще - где, кроме Си++, принят термин RAII?

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

>> Ты лучше скажи, чем это не finally?

Ну да, оно накручено вокруг finally (unwind-protect если быто точным), ну и что? Ресурсы освобождаются гарантированно и котролируемо при уничтожении объектов (если считать таковым выход из lexical scope) Захватываются при инициализации объектов. Какая нафиг разница как оно там внутри устроено?

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

> Ну да, оно накручено вокруг finally (unwind-protect если быто точным), ну и что?

Ну и всё. RAII - это попытка (не очень удачная) обойтись без finally.

> Какая нафиг разница как оно там внутри устроено?

Название RAII не подходит, всего-навсего.

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

>> Я спросил, на что больше похожи with-блоки - на finally или на RAII в понимании Си++. Ты ответишь? Еще - где, кроме Си++, принят термин RAII?

Похоже оно на finally, и что с того? То что в понимании с++ это должно работать как это работает там еще не значит, что оно там сделано единственно возможным способом. Блин ну че далеко ходить то, ООП а-ля С++ - яркий тому пример.

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

Хохохо!

Отличный вопрос!

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

Вот некоторые противопоставления:
1. Нативный код-виртуальная машина. В общем-то, честно сказать, я не вижу преимуществ виртуальных машин. На самом деле, они не дают преимуществ, кроме того, что якобы можно свалить проблемы переносимости на разработчика языка. Причём, эти проблемы можно свалить на разработчика и в случае нативного кода. При прочих равных рекомендуется нативный код, но в наше время это становится всё менее доступным.
2. Сборка мусора-явное управление памятью. Нужно знать и уметь работать с обоими вариантами. В основном, сборка мусора предпочтительна, кроме отдельных случаев. Хотя и у неё есть свои ловушки. Явное управление памятью необязательно означает явный delete и new. Это может быть и размещение на стеке и модель владения. Подсчёт ссылок я бы тоже отнёс к частному случаю явного управления. Впрочем, я с ним никогда не работал.
3. Динамизм-статичность. Динамизм хорош, чтобы подкрутить в рантайме работающую программу. Основные примеры динамизма - это операционная система (состоит из программ и скриптов, которые можно менять без остановки ОС), SQL сервера (состоит из таблиц, хранимых процедур и других объектов, к-рые можно менять без остановки сервера), Веб-сервера (контент меняется динамически), Common Lisp (многое можно менять без остановки лиспа), Python (что-то вроде можно менять, хотя я не знаток), clojure и наверняка ещё многие современные языки.

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

Продолжение следует...

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

Хохохохо (продолжение)

Из этого вытекает следующое противопоставление:
4. Динамическая-статическая типизация. Начиная с определённого масштаба, динамическая типизация должна быть допустима. Статическая типизация - это удел маленьких программ. Опять же, большинство тупиц этого не понимает. С другой стороны, статическая типизация придаёт программе надёжность и хорошо влияет на быстродействие. Влияние типизации на выразительность кода двояко. Динамическая типизация допускает больший полиморфизм, а статическая даёт контекст, в котором код становится более однозначным. Говоря по-Русски, мы иногда хотим сказать что-то конкретное, а иногда тяготеем к обобщениям. Нельзя сказать, что нужно всегда говорить конкретно и всегда общо. Нормальный язык должен давать обе возможности. В реальности я считаю практичным компромисс, когда типы могут генерироваться как в статике, так и в рантайме, при этом существуют "коробочки", дающие возможность хранить информацию о типе вместе с объектом, получая нужную степень полиморфизма там, где это действительно нужно. Я знаю только один язык, который полноценно реализует эту возможность - это SQL.
Также есть ещё одна очень важная вещь - возможность полиморфной инициализации. В С и подобных языках нужно сначала задекларировать тип переменной. Хотя можно вместо этого принять некие соглашения, позволящие писать polymorphicArray x = {1,"sdfasdf",new foo())}
Это - большое ограничение на С- образные языки, которое мешает в работе. Нужно изучить другие языки, чтобы понять, что это ограничение излишне. Например, в Object Pascal есть open array. Ну, я уже не говорю про Лисп...

5. Изменяемые-неизменяемые данные и сюда же относится транзакционность. Чисто функциональные языки пытаются работать со структурами, которые можно только создать, но нельзя редактировать. Многие среды поддерживают транзакции как способ обезпечения атомарности и обратимости операций. Оба эти подхода более-менее полезны (особенно, транзакции). Но они имеют ограничения. Наша жизнь необратима. Мы живём и совершаем поступки в условиях неопределённости, которые влияют на всю дальнейшую судьбу. Модель вычислительной чистоты неадекватна для решения задач реального мира. Она имеет право на существование в определённых областях (их не очень много), но должны быть предоставлены средства, чтобы разграничить её от императивной части, при этом, не осложняя жизнь. В этом смысле, Хаскель является очень пагубной и опасной религией, которая провозглашает, что чистые вычисления лучше необратимых действий. И вводит наказание за необратимые действия. Это - бред. Как и обычно бывает в религиях, у входа стоит мужик с дубиной, который "проверяет" всех приходящих на конформизм. После того, как ты прошёл через этого мужика, дальше всё может казаться стройным и логичным. Т.е., основная ложь любой религии кроется в самых её основах. Это имеет отношение и к Хаскелю. В роли мужика выступают старослужащие (что естественно), в роли дубины - понятие монады. Это понятие целенаправленно запутано, чтобы шокировать новичка. При этом, общий смысл понятия состоит всего лишь в лицемерном скрытии императива. В общем, я бы оценил Хаскель как достаточно грамотно сконструированную секту, хотя я бывал в сектах и покруче. Модель транзакций всё же адекватна жизни, причём есть многоверсионная модель и модель, основанная на блокировках. По правде говоря, мне ближе вторая, хотя не все со мной согласятся.

ещё продолжение будет...

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

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

6. Потоки выполнения (нити, процессы). Некоторые языки обладают врождёнными средствами параллельности (SQL, Java, clojure, Erlang). Это не моя сильная сторона, поэтому я промолчу. Однако нужно иметь представление о разных путях обезпечения параллельности. Я только скажу, что стремление выработать "общие" механизмы приводит к извращениям. Пример тому - популярность MYSQL. MYSQL использует блокировки таблиц, которые считаются не Ъ, однако, он популярен. Программировать с мультиверсионными транзакциями иногда оказывыется труднее, хотя вроде бы они представляют из себя более Ъ механизм.

7. Пространства имён. Эта идея довольно тривиальна, но она критично важна для достижения приемлемой производительности труда при программировании в больших масштабах. Один из ключевых недостатков Common Lisp (из-за которых я его не рекомендую) - это плохой дизайн пространств имён. Примеры хорошего дизайна - SQL и Pascal. С++ вроде тоже ничего.

8. ООП. ООП - это одна из вредоносных концепций. Полезного в ней - это структурирование программной среды. Когда код и данные принадлежат классам, это структурирует пространство имён. Фактически, каждый класс задаёт пространство имён и это позволяет структурировать программу. У этого подхода есть альтрнатива - организовать сущности в дерево. Первый тому пример - это файловая система. Второй пример - tcl.

Полиморфизм - это тоже хорошая идея, но она отвартительно реализована в С++. Java с наследованием интерфейсов в этом плане лучше. Наследование - это самая вредоносная из всех идей ООП, особенно, когда она сочитается с ограничением доступа к данным объекта. Также есть другой смысл ООП - представление программы в виде набора объектов, обменивающихся сообщениями. Я не преуспел в этом и мне эта парадигма не близка. Проблема тут - в том, что такой подход размазывает ответственность за правильность поведения между объектами. Объекты, по идеологии должны быть отдельными, но функционирование системы зависит от их взаимодействия. С моей точки зрения, многопоточное императивное программирование более плодотворно.

9. Сериализация. Хороший язык должен представлять средства для непринуждённого ввода-вывода данных. В этом плане С/С++ - это вообще полный мрак. XML - это ущербный формат, который плохо читается и человеком, и машиной. Более-менее пригоден json. Здесь я рекомендую изучить ввод-вывод списков, векторов, структур в Common Lisp. Это - одна из самых сильных сторон этого языка.

10. Метапрограммирование. Метапрограммирование содержит, как минимум, следующие состовляющие: - задача порождения кода - задача анализа кода - декларативное программирование - модификация процесса компиляции - рефлексия времени выполнения

Хрестоматийный пример реализации первого подхода - Common Lisp. Хотя я бы для изучения этого подхода рекомендовал изучить shell и m4 - те же идеи, но в более доступной и полезной для жизни форме. Примером низкоуровневой реализации этого подхода является Forth. Также массированная генерация кода происходит в веб-фреймворках, правда, тут нет ясности проявления идеи, потому что используется много разных языков. Красивым всё это было бы, если бы использовался лиспо-образный язык, обладающий одинаковым представлением. Т.е., если бы можно было заменить PHP, Javascript и html одним единым языком. Лисп, кстати, подходит для этого.

Может быть, для иллюстрации идей МП неплох php, хотя я его не знаю совсем. В принципе, код нормально генерируется на любом языке, у которого строковые константы могут переноситься на следующую строку и у которого есть полиморфизм параметров функции. С и Pascal не обладают такой возможностью и это просто уё.....

Пример де-факто стандартов как не надо генерить код - это cpp (препроцессор С и С++) и шаблоны С++.

Анализ кода видимо, лучше всего решен в промышленности для Javа с её рефакторингом и прочими вещами. В принципе, чем статичнее язык, тем легче его анализировать и тем труднее на нём писать. Я не знаю языка, который достигал бы здесь злотой середины. Это мог бы быть лисп, но он слишком расширяем.

Пример расширяемого компилятора я знаю только один - Common Lisp. Он совершенен в том отношении, что при этом генерит ещё и быстрый нативный код.

Основные примеры декларативных языков, используемых в промышленности - это SQL и make. Можно делать декларативные языки на чём угодно (для этого нужна всего лишь возможность генерировать код). Декларативный язык времени выполнения реализуется сложнее - требуется динамичность среды выполнения. Однако, это возможно в рамках динамичных сред, таких, как операционная система, веб-приложение, Java-машина или sql сервер.

11. Компоновка с внешними программами. Это не моя сильная сторона. Самое красивое, что я здесь видел - это встраивание OLE Automation в Delphi. В Visual Basic, видимо, встраивается ещё красивее. Одно только рекомендую: не пытаться линковать библиотеки, написанные на С++. Их не так уж много, чтобы ради этого так мучаться. Хотя в принципе, для этого есть SWIG.

12. ФП. Основная идея ФП - это замыкание. В принципе, замыкания возможны в любых языках, вопрос только в том, удобно ли это будет как синтаксис. Но идею знать нужно.

Ну и в итоге - рекомендации (из того, что знаю или в чём уверен) Рекомендую следующие языки для изучения соответствующих аспектов: - SQL (динамическая среда, декларативный язык, реляционный язык, транзакции, исключения, пр-ва имён таблиц в запросах) - clojure (почти идеальный язык на хорошей платформе. Очень много полезного, но не увлекаться "чистотой") - javascript (замыкания, ООП в виде простой иллюстрации) - shell,m4 (генерация кода в кристально чистом виде) - object pascal (прагматичный язык для промышленной разработки. open array, наследование интерфейсов, variants, ole automation, обработка исключений, модульность. Увы, нехватка макросов приводит к большим напрягам) - C (longjmp) - java (МП как анализ кода) - swig (для несчастных, которые захотят биндить библиотеки не С++) - php (прагматичный скриптовый язык для общего развития, хотя я его не знаю)

Не рекомендую: С++ (неудачная идея и реализация). В С++ есть только одна хорошая вещь - это возможность защищать ресурсы при раскрутке стека, создавая объекты на стеке. Однако, эта возможность легко достигается в любом расширяемом языке. Достаточно иметь нормальный макропроцессор. Haskell (слишком сектантский) Common Lisp (заменить на clojure). Т.е., выучить Commmon Lisp стоит, но не стоит на нём работать. Хотя я сам его использую и может быть, мне просто кажется, что он такой плохой :)

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

Из частоты приведения Коммон Лиспа в пример в твоем монументальном, так сказать, труде, я делаю вывод, что, по твоему мнению, Коммон Лисп - это где-то очень близко к идеалу. На столько близко, что на основе его идеологии конфетка делается весьма легко (Clojure) :)

Хотя мне лично не нравится его базирование на jvm. Вот наверняка же у любого языка на jvm ограничения будут ограничения самой jvm.

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

>> 8. ООП. ООП - это одна из вредоносных концепций. Полезного в ней - это структурирование программной среды. Когда код и данные принадлежат классам, это структурирует пространство имён. Фактически, каждый класс задаёт пространство имён и это позволяет структурировать программу.

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

>> 12. ФП. Основная идея ФП - это замыкание. В принципе, замыкания возможны в любых языках, вопрос только в том, удобно ли это будет как синтаксис. Но идею знать нужно.

Основная идея ФП не в замыканиях, а отсутствии побочных эффектов, а замыкания, higher-order функции и проч. - это уже рющечки.

>> Один из ключевых недостатков Common Lisp (из-за которых я его не рекомендую) - это плохой дизайн пространств имён

А поконкретнее можно?

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

>> Один из ключевых недостатков Common Lisp (из-за которых я его не рекомендую) - это плохой дизайн пространств имён

> А поконкретнее можно?

Достаточно прочитать хотя бы в одной книжке, как в CL реализованы пакеты.

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

>> 5. Изменяемые-неизменяемые данные и сюда же относится транзакционность [...]

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

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

>> Достаточно прочитать хотя бы в одной книжке, как в CL реализованы пакеты.

Ты не мудри ты пальцем покажи, что там плохо реализовано.

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

>> Хотя мне лично не нравится его базирование на jvm. Вот наверняка же у любого языка на jvm ограничения будут ограничения самой jvm

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

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

> По крайней мере в том, что он растет из jvm есть одно неоспоримое преимущество: огромная жабовская библиотека на все случаи жизни.

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

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

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

а лишняя математизированность - это как? где граница нелишнести?

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

> Ты не мудри ты пальцем покажи, что там плохо реализовано.

namespace a { namespace b { abc; namespace c { ... stuff ... }}}

a::b::c::stuff->something(a::b::abc);

Сделай такое в CL.

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

> а лишняя математизированность - это как? где граница нелишнести?

Как всегда, основным критерием выступает достаточность. Для забивания мебельного гвоздя достаточно среднего размера молотка, копёр здесь не нужен. У нас в городе ПТУ готовят каких-то программистов, которые где-то реально на каких-нибудь Делфях пишут программы. Значит, они востребованы. Но Хаскелль не в каждую голову с высшим образованием влезет, что про ПТУ говорить.

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

>> Сделай такое в CL.

Т.е. основная претензия - это то, что в лиспе нет вложенных пакетов? А какой в этом смысл? Ну предположим можно организовать некую иераррхию пакетов\пространств имен. Ну дык это можно и без вложенных пространств сделать воспользовавшись некими правилами именования пакетов, например (a#b#c::foo f#e::bar). Единственное, что остается это, как в втоем примере, доступность "abc" из пространства "c", ну дык с учетом naming conventions выглядит вот так:

(defpackage a#b#c
(:use a#b))

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

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

>> а лишняя математизированность - это как? где граница нелишнести?

mv уже ответил, от себя добавлю, что такие вещи как теория категорий, о которой так любят упоминать в литературе по хаскелю, если и преподается, то на специальностях к программированию отношения не имеющих вообще. А обычному программеру, у которого курс ВМ закончился матаном, ни или дискреткой, про которую он вспоминает как страшный сон, вникать в абстратную математику ну совсем тяжко. Оно конечно может и не надо глубоко туда нырять, но чувство стойкого отвращения при первом знакомстве с языком будет обеспечено, особенно когда вместо привычного и понятного a=b, он увидит нечто со странным названием - монада. И что он скажет? "Ахренеть!"

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

>>дискреткой, про которую он вспоминает как страшный сон

>и кому он такой нужен?

Забытая дискретка не означает плохого прогера ;)

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

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

Если говорить именно о языке clojure как об очередном диалекте лиспа со своими нюансами синтаксиса и заложенными идеями (*), то да, согласен. А если говорить о функционале в виде уже готового кода из JavaSE/EE, ready to use, то не соглашусь.

(*) я в этом плане вообще не понимаю нафига нужны языки сделанные по принципу "с мира по нитке": возьмем чуть чуть из перла, чуть-чуть из смалтолка, чуть чуть из паскаля (алгола) - опа, получился руби. Скрестим Си с перлом - получился ПХП, ну и так далее в том же стиле. А как результат - море безидейных уродцев, рожденных от желания одного человека заиметь новый синтаксис со старой семантикой.

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

>> Забытая дискретка не означает плохого прогера ;)

> внезапно. а что же в таком случае означает?

"Не пригодилась" (c)

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

>> и кому он такой нужен?

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

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

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

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

Чем глубже и сильнее теория, стоящая за программой, тем программа получается лучше и качественнее. Правда халатного отношения теория не терпит. Типичный пример -- оригинальные регэкспы и перловые(pcre). Напомнить разницу между ними? :)

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

> Если какие-то несложные прикладные задачи
...
> то да, не пригодятся группы, кольца

верно.

следует ли из этого, что для написание _сложных_
задач они непременно пригодятся?

> Чем глубже и сильнее теория, стоящая за программой,
> тем программа получается лучше и качественнее

где я могу почитать про глубокую теорию, которая является
фундаментом, скажем, linux kernel?

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

> следует ли из этого, что для написание _сложных_ задач они непременно пригодятся?

Естественно нет. Зато в случае их использования мы получаем определенные стопудовые и заранее известные свойства программы. Разве это не достойный профит?

> где я могу почитать про глубокую теорию, которая является фундаментом, скажем, linux kernel?

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

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

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

Мозг прочищает и упорядочивает. Сильно.
К примеру, приходит понимание, что operator< не обязательно задаёт полный порядок; знак "плюс" означает не сложение чисел, а некоторую бинарную операцию; что отображение объектов на их хеш-коды не сюръективно и даже не инъективно и т.д.

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

> Мозг прочищает и упорядочивает. Сильно.

Где бы потом работу найти таким, с прочищенными мозгами? :)

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

>"Не пригодилась" (c)

ты вопроса не понял. что означает плохого прогера? какой критерий, если не знание той же дискретки?

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

> Т.е. основная претензия - это то, что в лиспе нет вложенных пакетов? А какой в этом смысл?

В С++ двухуровневая система исключений. А какой смысл в трёхуровневой? В Си нет понятия объекта, но в структуру можно ложить указатели на функции. Какой смысл тогда в отдельных понятиях класс и объект? В CL у elt первый параметр - последовательность, второй - индекс, а у более частного nth - наоборот. Ну и что? Подумаешь, проблема...

Продолжать можно бесконечно.

> Совсем маленький оверхед, но это работает.

Любой костыль нарушает стройность хода.

> А вот чего нет в си++-ных наймспэйсах, так это, например, контроля того, что экспортируется из пространства.

В плюсах по сравнению с Лиспом много чего нет, можно и не напоминать.

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

> ты вопроса не понял. что означает плохого прогера? какой критерий, если не знание той же дискретки?

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

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

>В твоём месте обитания как-то иначе?

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

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

> в моём месте обитания без знаний дискретки ему будет непросто выполнить поставленные задачи в срок

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

А кому-то нужны дифуры. Или микроэлектроника. Мне вот не помешала бы физика, линейка и риторика с психологие %)

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

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

это вроде не дискретка. или у нас разные о ней понятия :)

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

> что отображение объектов на их хеш-коды не сюръективно

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

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

>> Мозг прочищает и упорядочивает. Сильно.
> Где бы потом работу найти таким, с прочищенными мозгами? :)


Это даже срантехнику поможет, не только программисту.

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

>> не сюръективно и даже не инъективно
> функция имеет обратную iff она биективна :)


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

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

>> что отображение объектов на их хеш-коды не сюръективно
> c чего бы отображение (хеш-функция) было не сюръективно, если множество значений и есть множество хеш-кодов?


А с того, что так бывает в узком и никому не нужном частном случае.

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

>Ололо, у нас на мехмате это было на первой же лекции по алгебре

что именно, и какую позицию ты отстаиваешь?

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

>что именно

Биективность функции, д-во "ф-ция f имеет обратную" <=> "ф-ция f биективна".

>и какую позицию ты отстаиваешь?

Позицию пока что никакую не отстаиваю, так как еще целиком не прочитал тренд.

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

>Биективность функции, д-во "ф-ция f имеет обратную" <=> "ф-ция f биективна"

ну вот и славно. можно идти спать с чистой совестью

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

> Биективность функции, д-во "ф-ция f имеет обратную" <=> "ф-ция f биективна".

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

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

>Из частоты приведения Коммон Лиспа в пример в твоем монументальном, так сказать, труде, я делаю вывод, что, по твоему мнению, Коммон Лисп - это где-то очень близко к идеалу. На столько близко, что на основе его идеологии конфетка делается весьма легко (Clojure) :)

>Хотя мне лично не нравится его базирование на jvm. Вот наверняка же у любого языка на jvm ограничения будут ограничения самой jvm.


А мне не нравится (категорически) что clojure не компилирует в class-файл - как на нём делать библиотеки и не грузить потом приложение пол дня?

Или я отстал от жизни?

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

>Забытая дискретка не означает плохого прогера

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

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

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

Какой "школой" - ВУЗ имеется в виду?

> не годятся для чего-либо интересного.

Он могут не годится для того, что считаешь интересным _ты_, но ты не истина в последней инстанции. И опять же, могут и годится - люди с течением жизни меняются, и на следующем свидании дискретка уже не вызовет отвращения.

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

> доказательство провести, или сам справишься?

Отлично, докажи мне биективность хеш-функции f(int x)=x%2. Гнилой помидор уже готов к броску.

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

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

По-моему, если у человека есть ясное понимание вопроса, то он подберёт наиболее естественные и простые слова Русского языка и скажет так, что будет понятно и второкласснику. А если сказать нечего, будет строить забор из заумных слов. Но тут он сам попадёт в ловушку. Слово весит и занимает ресурсы мозга. Происходит фрагментация сознания. На том же мехмате я был озадачен тем, как одни и те же понятия вводились под разным соусом сначала в матане, потом в функане, потом в тервере. Слава Богу, я уже забыл 90% того, чем мне там пытались забить голову :)

Вот тут продвинутый товарищ по имени cathode не понимает, зачем в языке программирования нужна иерархическая организация сущностей. Либо он никогда не пользовался файловой системой, либо это так дискра мозги промывает - я уж не знаю :) Я предлагаю в качестве упражнения отказаться от вложенных директорий на пару недель :) Т.е., /home можно иметь, а /home/cathode - ни-ни!

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

Но проблема с пр-вами имён в Common Lisp - не в том. Она - в том, что нет защиты от ошибок. Если код написан с расчётом, что есть такой символ foo, взятый из пакета bar, а на самом деле, такого символа нет, то символ будет молча создан и мы узнаем об ошибке только тогда, когда напоремся на отсутствующее смысловое содержание этого символа. А это будет не сразу (и здесь подлянку приготовила динамическая типизация).

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

Все эти факторы в совокупности создают трудную практическую проблему. Я потратил немало сил, чтобы её решить, но до сих пор я мучаюсь с тем, чтобы разбить свою разросшуюся библиотеку на логично обособленные части.

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

>> c чего бы отображение (хеш-функция) было не сюръективно, если множество значений и есть множество хеш-кодов?

> А с того, что так бывает в узком и никому не нужном частном случае.

Например md5 хэш - сюръективная функция (для любого 128 битного числа найдется прообраз). Это "узкий и никому не нужный частный случай"?

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

>>>> функция имеет обратную iff она биективна :)

>>> так и запишем, не помнит ревнитель дискретки предмет своего обожания

>> доказательство провести, или сам справишься?

> Отлично, докажи мне биективность хеш-функции f(int x)=x%2.

Сначала придется кому-то доказать, что эта функция имеет обратную :)

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

>> Биективность функции, д-во "ф-ция f имеет обратную" <=> "ф-ция f биективна".

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

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

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

>> Вот тут продвинутый товарищ по имени cathode не понимает, зачем в языке программирования нужна иерархическая организация сущностей.

Товарищь понимает. Товарищь не понимает, почему приплюснутые нэймспэсы хуже пакетов лиспа.

>> Я предлагаю в качестве упражнения отказаться от вложенных директорий на пару недель :)

Дерзай!

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

>Какой "школой" - ВУЗ имеется в виду

Это кому где прививали отвращение к математике:) Раньше AFAIR это делали в средней школе, сейчас не знаю.

>для того, что считаешь интересным _ты_

Само собой! Именно поэтому там было слово "интересный", подразумевающее наличие интересующегося.

>люди с течением жизни меняются

Функциональщики говорят, что это уже _другие_ люди:)

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

> Товарищь не понимает, почему приплюснутые нэймспэсы хуже пакетов лиспа.

Вроде бы говорилось, что они (namespace'ы из Си++) как раз _лучше_ пакетов CL.

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

>Отлично, докажи мне биективность хеш-функции f(int x)=x%2. Гнилой помидор уже готов к броску

ты белены объелся? каким образом из моего утверждения следует что у эта функция биективна? или ты готов предоставить обратную к ней функцию?

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

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

Это проблема конкретно взятого компилятора и его настроек, а не языка.
Пжалста, вот что выдаст sbcl:

(defpackage :test)
(defun xxx () test::qwerty)
(compile 'xxx)

WARNING in XXX :
TEST::QWERTY is neither declared nor bound,
it will be treated as if it were declared SPECIAL.

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


ИМХО, это уже к языку мало относится.

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

>> Вроде бы говорилось, что они (namespace'ы из Си++) как раз _лучше_ пакетов CL.

Извиняюсь, зарапортовался.

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

>> это вроде не дискретка. или у нас разные о ней понятия :)

Это уже почти хаскель :))

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

>Функциональщики говорят, что это уже _другие_ люди:)

именно что! зато никаких тебе race conditions в общении с ними :)))

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

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

Естественно, это было сказано с единственной мыслью мехмат затроллить. Надо же узнать, кто из присутствующих в треде знает "матан".

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

> Это проблема конкретно взятого компилятора и его настроек, а не языка.
Это проблема языка. Я же сказал: проблемы выявится, когда мы наткнёмся на отсутствие смысла в символе. Просто в твоём случае это случилось сразу (а иначе и быть не могло, когда всего три строки). Не все случаи так просты, как приведённый. И возникающая при этом сложность может быть охарактеризована как "плохая масштабируемость".

Но заметь, что символ qwerty в пакет test внедрился _молча_. Если бы ты написал test:qwerty, то ридер бы ругнулся. На практике, приходится (и довольно часто) пользоваться внутренними символами из других пакетов. Почему? Потому что ты не можешь безболезненно экспортировать символ - могут возникнуть конфликты в использованных пакетах и задолбаешься их вылавливать. Т.е., конечно, можно вообще не использовать пакеты и тогда у нас всё будет как в старом добром С - все имена всегда нужно полностью квалифицировать. Что эквивалентно отсутствию такого понятия, как пространства имён, вообще.

Ещё одна ситуация. Бывает, что ты рассчитываешь, что символ был импортирован в твой пакет, а он не был импортирован. Т.е.,

(defpackage :test (:use :cl :foo))
; Раньше был символ foo:bar, а теперь его нет, т.к. после
; рефакторинга он попал в :quux. А поскольку foo у нас используется,
; то не пишем квалификатор.
(in-package :test)
(bar) - молча создаётся новый символ bar вместо ссылки на (переехавший) quux.bar.

<еще 200 строк мусора, если это в файле>
Ошибка/предупреждение: функция bar не определена

Что происходит дальше? Дальше нужно стереть все fasl-ы, где этот bar мог использоваться, перезапустить образ и загрузить всё по новой (а это занимает минуту и больше). И так далее много раз. Можно пытаться срезать путь и не перезагружать, но это, скорее всего, выйдет боком. В динамической среде все ошибки остаются в образе до тех пор, пока их не исправили. Если неверное определение функции лечится более-менее легко (при отсутствии inline её достаточно перекомпилировать), то ошибка в пространстве имён лечится тяжело.

> ИМХО, это уже к языку мало относится

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

Я на самом деле, эту проблему победил, пока что для одной реализации - мне удалось подменить функции find-symbol и intern в лиспворксе и я завёл список запретных имён. При попытки intern-ить запретное имя в неправильный пакет я порождаю ошибку. Только после этого я начал чувствовать себя более-менее в безопасности. А до этого не было никакой другой возможности рефакторить, кроме как перебрать ВСЕ определённые функции и переменные по одной и искать их во всех местах? где они используются. Что непроизводительно. В С и Паскале это решается проще - ты просто переносишь определения, запускаешь компилятор и ловишь сообщения об ошибке.

Я, кстати, ещё не рассказал о том, что продвинутый лисп крайне редко показывает место ошибки при компиляции файла. Его обычно нужно отыскивать с помощью телепатии и ясновидения. Одно это уже позволяет не рекомендовать лисп для промышленного применения. Если же пользоваться asdf (а придётся пользоваться), то в некоторых случаях придётся пользоваться инспектором, чтобы узнать имя файла и даже чтобы прочитать само сообщение об ошибке! Таким образом, замечательные метавозможности и прекрасный внутренний дизайн лиспа полностью компенсируются неудобством практической работы с ним. Мы видим слабость приложений и библиотек и это - самое неоспоримое доказательство того, что производительность труда при работе на лиспе низка.

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

>> В вакууме вообще трудно общаться :)

> признайся - ты просто никогда не пробовал ;)

Ooops... you found out. Now we have to kill you.

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

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

В SBCL (наверное, вообще в любой реализации CL, но не уверен, поэтому только SBCL) сама лисповая часть, не имеющая отношения к низкоуровневой реализации, логически разбита на две части: сама имплементация базовых фич Лиспа и написанные уже сверху Коммон-Лисповские библиотечные стандартности. Систему пакетов как раз не очень сложно переписать, но это уже будет не CL ;) Но переписать можно.

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

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

> Например md5 хэш - сюръективная функция (для любого 128 битного числа найдется прообраз). Это "узкий и никому не нужный частный случай"?


Покажи, где это применяется. (Кроме доставания болванки из хеш-кода через astralctl)

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

>> Отлично, докажи мне биективность хеш-функции f(int x)=x%2.
> Сначала придется кому-то доказать, что эта функция имеет обратную :)


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

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

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

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

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

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

Да, похоже. Фигурный квотинг делает из меня неадеквата.

P.S. А тут ещё злой пи скор откусывает :)

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

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

А где здесь речь про хеш-функцию:

>>>> функция имеет обратную iff она биективна :)

>>> так и запишем, не помнит ревнитель дискретки предмет своего обожания

>> доказательство провести, или сам справишься?

???

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

>> Да-да, пусть он сначала предъявит мне обратную функцию для произвольной хеш-функции.
> А где здесь речь про хеш-функцию:


Разобрались уже. кое-кто баловался фигурным квотингом.

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

> Уймитесь вы уже со своей сюръективностью. Есть более простые слова - однозначное, взаимно-однозначное и т.п. Все нормальные кодеры прекрасно понимают эти понятия и без специальной математической терминологии.

Если кодеру объяснить что-то "на пальцах", потом он всегда этим объяснением и будет пользоваться, снова и снова прокручивая его в уме. Как первоклассники лет 100-150 назад считали на пальцах и только на пальцах, потому что их так обучили.
Пример: один мне встречавшийся овощ разницу между клиентом и сервером постоянно выводил из прочитанной им когда-то статьи о клиент-серверном вирусе. До кучи ещё и неправильно выводил :)

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

> Покажи мне, как применяется факт того, что md5-отображение сюрьективно.

Если бы md5-отображение было не сюръективно, а использовало, например, 1% от всех 128 битных чисел, то было бы больше коллизий и находить их было бы проще.

А вообще, изначально кто-то утверждал, что сюръективные хеш-функции "бывают в узком и никому не нужном частном случае". Что, очевидно, не верно.

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

>> Покажи мне, как применяется факт того, что md5-отображение сюрьективно.
> Если бы md5-отображение было не сюръективно, а использовало, например, 1% от всех 128 битных чисел, то было бы больше коллизий и находить их было бы проще.


А если бы 2^128-1? Много проще бы стало?

> А вообще, изначально кто-то утверждал, что сюръективные хеш-функции "бывают в узком и никому не нужном частном случае". Что, очевидно, не верно.


Факт сюръективности никак не используется => "не нужно".

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

>> Просто в твоём случае это случилось сразу (а иначе и быть не могло, когда всего три строки).

В моем случае это случилось во время компиляции, не важно в вобщем...

>> Что происходит дальше? Дальше нужно стереть все fasl-ы, где этот bar мог использоваться, перезапустить образ и загрузить всё по новой (а это занимает минуту и больше).

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

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

Это у тебя LispWorks так работает? При компиляции slime+emacs показывает все проблемные места, тыкай мышкой и получай описание ошибок.

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

Ты хотел сказать не существует нормальной среды разработки?

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

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

>> А до этого не было никакой другой возможности рефакторить, кроме как перебрать ВСЕ определённые функции и переменные по одной и искать их во всех местах? где они используются. Что непроизводительно. В С и Паскале это решается проще - ты просто переносишь определения, запускаешь компилятор и ловишь сообщения об ошибке.

Оригинальный способ рефакторинга, я доложу! Во-первых открой для себя slime, а в нем crossrefernce. Во-вторых у тебя очень странные представления о рефакторинге С и Паскаля, обычно в ихних IDE достаточно жмакнуть пимпу Refactor и оно само переместит/переименует/добавит/удалит все что надо.

>> В динамической среде все ошибки остаются в образе

В статической среде все ошибки остаются в файлах.

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

> При компиляции slime+emacs показывает все проблемные места, тыкай мышкой и получай описание ошибок
> Во-первых открой для себя slime, а в нем crossrefernce


Во-вторых, открой для себя asdf и убедись, что мышкой станет тыкать некуда. Ну и кроме того, при той ошибке, о которой я говорю, даже в одном файле тыкать некуда, потому что ошибка будет в конце файла и сказано в ней будет "ссылка на неопределённую функцию". И я не понял, какое отношение cross-reference имеет к рефакторингу.

> Во-вторых у тебя очень странные представления о рефакторинге С и Паскаля, обычно в ихних IDE достаточно жмакнуть пимпу Refactor и оно само переместит/переименует/добавит/удалит все что надо


Возможно, я не пользовался такими фичами. Хотя мне кажется, что ты немного завираешься, если речь идёт о С. Но если это правда, то тем хуже для лиспа. В нём нет кнопки "refactor", хотя язык вроде бы такой весь из себя крутой!

> Ты хотел сказать не существует нормальной среды разработки

Я уже два раза сказал, и мне кажется, что достаточно однозначно :)

> А про слабость приложений и библиоек не понял, что ты под этим подразуеваешь?

Я подразумеваю ровно то, что вижу. Приложений я вообще не вижу на лиспе. Библиотеки убогие. Примеры? Да сколько угодно.

clsql - нет параметризованных запросов
сl-ppcre - не умеет парсить потоки, а умеет только строки
alexandria - вообще очень маленькая и слабая библиотека
tinaa - ладно, что тормозит и неправильно работает под win32, я не смог вообще сгенерить документацию для своего проекта - мне сказали "класс nil не найден". Это после того, как я потратил полчаса времени на то, чтобы её собрать и пофиксить один баг. Плюнул после этого. Но даже если бы не плюнул, то сравнить с Doxygen её нельзя. Doxygen круче в 10 раз, хотя написан "всего лишь" на С.
asdf - вообще, кроме мата, никаких других слов. Это надо испытать, чтобы понять. Хотя, если выучить исходники наизусть и программировать отдельно под каждую систему, даже можно работать.
clbuild - может собирать только последние версии. Т.е., unstable всегда (и кстати, он в основном написан не на лиспе, а на шелле. Автор даже как бы извинялся :)
asdf-install - стабилен, но чё-то там много тухляка. Как правило, рекомендуют брать текующую версию из репозитория.

Т.е., не существует ничего похожего, скажем, на релизы, как в дебиан. Либо у тебя trunc, либо устаревший и несогласованный между собой тухляк. Можно гарантировать, что разработка чего-нибудь сложного займёт немало времени из-за постоянных обновлений библиотек.

sbcl - ты никогда, ни при каких флагах компиляции не увидишь имена всех своих переменных. Что-то увидишь, но параметры - никогда. Некоторые кадры стека будут уничтожены при любом раскладе и ты вообще их не увидишь. Я уже не говорю об отсутствии чего-либо похожего на визуальную отладку, о возможности поставить брекпойнт, о возможности увидеть результат макрорасширения иначе, чем вручную писать macroexpand. Был проект lispdebug, котрый всё это умел, но он похерился почему-то.

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

Всё это вместе выглядит похожим на большую помойку! Каждую проблему по отдельности можно было бы пережить, но они всё лезут и лезут изо всех щелей. И, самое главное - море СКОБОК!

Справедливости ради, конечно, нужно сказать, что на лиспе есть и гениальные проекты, например, ap5. Но они сделаны давно.

А есть ещё и другие проблемы в самом языке (совсем не маленькие и не смешные). Но я лучше пойду спать...

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

>Да юзай что угодно, только не называй это RAAI.

Почему? Где-то существует Комитет По Стандартизации Значений Плюсовых Аббревиатур?)

Имхо, RCSP (да, еще одна аббревиатура!:)) имеют полное право называться реализацией RAII. Другое дело, что не всегда их использование оправдано.

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

> Это есть только в Си++ (насколько я знаю).

Точно есть в D, а Педивикия говорит, что это также есть и в Аде.

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

>> Да юзай что угодно, только не называй это RAAI.

> Почему? Где-то существует Комитет По Стандартизации Значений Плюсовых Аббревиатур?)

Чтобы не обозначать одним термином разные вещи.

>> Это есть только в Си++ (насколько я знаю).

> Точно есть в D

IIRC, в D есть и конструкторы/деструкторы, так что в нем RAII можно сделать точно как в Си++.

> также есть и в Аде.

Самой Ады нет :)

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

> Самой Ады нет :)

Почему же? Как минимум есть в автоматической ветке Парижском метрополитена :) Еще есть на каких-то GPS'овых спутниках. Вообщем, пока есть :)

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

> сl-ppcre - не умеет парсить потоки, а умеет только строки

А что умеет? pcre со строками работает, ~= в перле со строками работает, boost:regex со строками работает. Там ведь вообще идеология работы со строками.

> sbcl - ты никогда, ни при каких флагах компиляции не увидишь имена всех своих переменных. Что-то увидишь, но параметры - никогда.

Это ты про что?

> Некоторые кадры стека будут уничтожены при любом раскладе и ты вообще их не увидишь.

Опять, ты про что?

> Я уже не говорю об отсутствии чего-либо похожего на визуальную отладку, о возможности поставить брекпойнт,

(break)?

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

В slime кнопки нажать можно.

> windows - до сих пор только коммерческие реализации нормально работают с тредами.

Смею предположить, что кому треды по винду нужны, тот сам сделать не может, а кто может, тому не нужны. Типичная ситуация.

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

>> Да юзай что угодно, только не называй это RAAI.

> Почему? Где-то существует Комитет По Стандартизации Значений Плюсовых Аббревиатур?)

> Имхо, RCSP (да, еще одна аббревиатура!:)) имеют полное право называться реализацией RAII. Другое дело, что не всегда их использование оправдано.

Ты можешь использовать что угодно, просто тебя никто не поймет. Увидев твой RAAI, я полез у гугл, но ничего понятного не нашел. Та же хрень в википедией. Про RAII, если не знаешь, то найдешь расшифровку. Разница лишь в том, поймут тебя или нет.

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

>> Возможно, я не пользовался такими фичами. Хотя мне кажется, что ты немного завираешься, если речь идёт о С. Но если это правда, то тем хуже для лиспа.

Кхм... Скажи честно, ты когда-нибудь Eclipse, NetBeans или MS VS видел?

>> В нём нет кнопки "refactor", хотя язык вроде бы такой весь из себя крутой!

А что, есть языки с кнопкой refactor?

>> И я не понял, какое отношение cross-reference имеет к рефакторингу.

Самое прямое.

>> Т.е., не существует ничего похожего, скажем, на релизы, как в дебиан. Либо у тебя trunc, либо устаревший и несогласованный между собой тухляк. Можно гарантировать, что разработка чего-нибудь сложного займёт немало времени из-за постоянных обновлений библиотек.

У-у-у друг, ты еще не видел какой тухляк творится в С,С++, Жаве, Перле и прочих языках... BTW, покажи мне язык для которого централизовно релизятся все-все-все библиотеки и я откажусь от лиспа.

>> sbcl - ты никогда, ни при каких флагах компиляции не увидишь имена всех своих переменных. Что-то увидишь, но параметры - никогда. Некоторые кадры стека будут уничтожены при любом раскладе и ты вообще их не увидишь.

Ну вообще-то чтобы увидеть имена переменных sbcl не нужен, ага.

>> Я уже не говорю об отсутствии чего-либо похожего на визуальную отладку, о возможности поставить брекпойнт, о возможности увидеть результат макрорасширения иначе, чем вручную писать macroexpand. Был проект lispdebug, котрый всё это умел, но он похерился почему-то.

Я тебе уже писал в прошлый раз, но повторюсь, открой для себя slime: macroexpand - C-c RET, breakpoint - (break), визуальная отладка - это слишком объемное понятие, чтобы понять, что конкретно ты имеешь в виду, подозреваю, что-то типа inspect, тогда C-c I. Лучше напомни язык, программу на котором можно отлаживать и перекомпилировать не останавливая саму программу, слабо? Один такой я знаю - smalltalk, остальных что-то не видать.

>> windows - до сих пор только коммерческие реализации нормально работают с тредами.

Ну меня это мало волнует. В конце концов, что тебе мешает использовать коммерческие реализации?

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

Emacs отлично работает под оффтопиком, и ни кто не запрещает тебе использовать твой любимый лиспворкс из Emacs-а.

>> И, самое главное - море СКОБОК!

Ну и брось его, програмь на чем-нибудь, что в состоянии осилить. Делов-то!

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

> BTW, покажи мне язык для которого централизовно релизятся все-все-все библиотеки и я откажусь от лиспа.

Разве в жабе и дотнете основные библиотеки платформы не релизятся точно вместе с новой версией платформы?

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


Tcl, Erlang

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

> Ну и брось его, програмь на чем-нибудь, что в состоянии осилить. Не понял, откуда у тебя впечатление, что я не в состоянии.

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

Можно осилить разные навыки, например, как трусы через голову одевать. Но нужно ли это? Я, освоив лисп в достаточной степени, могу сказать - нет. Не нужно. Отдельные идеи лиспа хороши, и даже их сочетания хороши. Но недостатки фатальны. Даже если бы сам язык был плохим, но было бы сильное сообщество, можно было бы мириться с этим. Но слабо также и сообщество. Не найдёшь работу - тяжело получить прибыль с вложенных усилий. Не найдешь специалистов - тяжело поднять свой бизнес. Итоговый вывод: common lisp не стоит труда.

Должен появиться какой-то новый язык на тех же идеях, менее грязный и бардачный, чем Common Lisp. Возможно, это уже появившаяся clojure. Возможно, Nemerle. Возможно, C# дорастёт до этого уровня. Не знаю. А сами идеи лучше изучать на более простых и явных примерах. Мысль о том, что эти идеи могут сочетаться в одном языке, может дойти до разумного человека и без изучения Common Lisp.

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

>> Ну и брось его, програмь на чем-нибудь, что в состоянии осилить.
> Не понял, откуда у тебя впечатление, что я не в состоянии.


Следи, кому отвечаешь.

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

> Разве в жабе и дотнете основные библиотеки платформы не релизятся точно вместе с новой версией платформы?

Основные библиотеки и в Lisp'е вместе с платформой. Претензии-то не к ним, а ко всяким CL-SQL (не нравится, бери Postmodern или CL-RDBMS), alexandria и прочим 3rd party libraries. В таком контексте я сейчас и для Java и для .Net накопаю полсотни условно работающего хлама (неоторый хлам даже за деньги(!) предлагают). Это что-то докажет?

А вопрос был про "все-все библиотеки". К слову, один такой язык я знаю: C + Debian repository :-) хотя в этом контексте Lisp + Debian работает не хуже.

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

> А вопрос был про "все-все библиотеки". К слову, один такой язык я знаю: C + Debian repository :-)

Сам же понимаешь, что это утопия.

> К слову, один такой язык я знаю: C + Debian repository :-) хотя в этом контексте Lisp + Debian работает не хуже.


Никогда не вставал на грабли с dev-пакетами? Ну ничего, ещё не вечер.

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

> Никогда не вставал на грабли с dev-пакетами? Ну ничего, ещё не вечер.

А ты встречал грабли с dev-пакетами в Debian-stable? Можно пример? Я всегда думал, что если они следят за стабильностью, то это глобально.

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

>> Никогда не вставал на грабли с dev-пакетами? Ну ничего, ещё не вечер.
> А ты встречал грабли с dev-пакетами в Debian-stable? Можно пример? Я всегда думал, что если они следят за стабильностью, то это глобально.


Безопасность(за которой действительно следят)!=стабильность. Кроме того, интересный тебе пакет может просто не оказаться в дистрибутиве.

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

> Основные библиотеки и в Lisp'е вместе с платформой

Cлушай, не смеши меня. Что там есть:
#+sbcl sb-ext:quit #+(or ccl lispworks) quit

Как минимум, в стандарте нет переносимой функции "выйти из лиспа". Также там нет:

- возможности узнать список аргументов функции (есть, но стандарт позволяет возвращать nil, что реализации радостно и делают)

- возможность узнать список полей структуры, хотя язык динамический и вроде бы рефлексивный. Только не надо меня лечить, что вместо структур надо пользоваться классами. Классы работают в 6-20 раз медленнее структур в нескольких реализациях, где я это проверял. Определение класса обычно втрое более объёмное, чем определение структуры. При этом, из-за своей гибкости, код с классами менее однозначен и, тем самым, более сложен для чтения. Кроме того, MOP тоже не стандартизован.

И ещё один перл:
в ccl #p"c:/systems/foo.asd.lnk" ->"c:/systems/foo'.asd.lnk"
при внимательном чтении стандарта выясняется, что physical pathnames - это implementation dependent вещь. Но нигде в стандарте не написано, что physical pathname - это имя файла, которое понимает операционная система. В ccl есть специальная (специфичная для реализации) функция для того, чтобы сделать понятное операционной системе имя файла из physical-pathname. Это нужно, например, для запуска внешней программы.

Т.е., в common lisp нету даже переносимого способа обращения к файлам!

Далее. Если попытаться сделать совершенно элементарную вещь - вызвать команду операционной системы и прочитать то, что она выводит, то и тут будут проблемы. Некоторые реализации не позволяют перенаправить выходной поток, некоторые - сливают вместе stdin и stderr. Я видел попытки сделать слой переносимости в asdf и в clsql, но нигде эта работа не доделана до конца. Под win32 всегда приходилось что-то патчить. Ну и, конечно, нет развязки по версиям реализаций.

О каких ещё "основных библиотеках" может идти речь после этого? Что конкретно ты имеешь под этим в виду?

В общем, это - полная помойка, а не среда разработки!

> Postmodern или CL-RDBMS

Я боюсь тратить своё время. Почему-то мне кажется, что они будут ещё кривее, чем CLSQL. Который, вроде бы, всё же удалось приучить к работе.

К слову, про "все" библиотеки лично я речи никогда не вёл. Это был демагогический приём моих оппонентов :)

> накопаю полсотни условно работающего хлама

Не знаю. Может быть, я в этом отношении так плохо думаю про лисп только потому, что не работал на Яве :) Хотя я читал мнения тех, кто пробовал и то, и другое, о том, что лисп как платформа слабее. Мне почему-то верится.

Но если говорить не про библиотеки, а про "стандартную библиотеку", то здесь есть ужасные пробелы. Например, нет полного набора коротких имён функций для работы с a-списками. Например, сравним получение элемента a-списка в лиспе:
(cdr (assoc key list)) - чтение
(setf (cdr (assoc key list)) new-value) - чтение
и в том же Object Pascal
list[key] - чтение
list[key]:=new_value;

да, я вру в том, что на самом деле, есть ещё &key и т.п., но почему всё же основная форма записи так длинна? Лисповый текст примерно вдвое длиннее паскалевого. Вдвое длиннее - это значит, что глазу нужно совершить вдвое больше работы для просмотра этой строки. А у меня есть такое предположение, что распознование изображений букв - это одна из наиболее трудоёмких (хотя и не осознаваемых) частей работы по чтению кода, если сам код достаточно прост. Во всяком случае, скомпилировать страницу кода на самом забористом С++ и распознать страницу кода со сканера - это задачи, отличающиеся по вычислительным ресурсам, наверное, раз в 500. Конечно, у мозга другая архитектура и задача распознавания, видимо, решается быстро за счёт параллельности. Но даже если этот коэффициент у человека равен просто единице, то всё равно потеря велика. Также нужно учесть и то, что и в мозгу есть разные кеши. Например, при чтении взглядом можно охватить только довольно небольшой кусок текста, что вызовет "атомарный акт понимания" и этот объём - это просто определённое количество букв. Если паскалевский/явовский/питоновский текст вдвое компактнее лиспового, то лисповый код может оказаться в 10 раз труднее для понимания из-за выпадения информации из кеша. Я на самом деле, думаю, что основная проблема лиспа - именно в этом. Просто, поскольку это тяжело выявить вне рамок специального исследования, мало кто из лисперов способен это заметить.

Если я прав, то какой вывод? Лисп плохо сказывается на производительности труда.

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

Также нет таких функций, как "заменить кусок строки на строку большей длины", "взять хвост строки". Да, всё это пишется. Но при этом каждый пишет такую функцию для себя. И при чтении нового кода нужно каждый раз потратить время на изучение новых соглашений об именах и нового синтаксического сахара. Например, есть такие, удобные, но не общепринятые вещи: length=, awhen, aif. Они нужны исключительно из-за гротескной непрактичности основного синтаксиса CL. Когда работаешь над разными проектами (особенно чужими), тебе нужно постоянно тратить ресурс мозга на то, чтобы помнить, какими конструкциями можно пользоваться, а какими нельзя. Когда ты напишешь свою функцию (например, я написал sequence-last), скорее всего, со временем возникнет конфликт имён с чьей-нибудь ещё одноимённой функцией (например, у меня возник конфликт с clsql:sequence-last). Заранее это не предугадать.

В общем, лисп - это гениальная, но несколько недоделанная среда разработки. Моя задача - зарабатывать деньги, а не бороться с последствиями того, что кто-то поленился доделать 20 лет назад (хотя это было легко доделать тогда). Теперь болезнь запущена и я бы прописал этому языку эвтаназию. Из гуманизма.

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

> (cdr (assoc key list)) - чтение
(setf (cdr (assoc key list)) new-value)
и в том же Object Pascal
list[key] - чтение
list[key]:=new_value;

А в С++
list.find(key)->second - чтение
list.find(key)->second = new_value

что не менее громоздко, чем Lisp. Наличие в Pascal синтакического сахара из коробки -- не аргумент

> Например, есть такие, удобные, но не общепринятые вещи...

реально они общеприняты. Также как CFFI, ASDF и прочие соглашения. Иначе можно считать, что ODBC в C/C++ тоже удобная, не общепринятая вещь :-)

> В общем, лисп - это гениальная, но несколько недоделанная среда разработки.


Если лисп = Common Lisp как стандарт, то видимо да. Нет MOP, нет потоков, нет FFI. Если Lisp как SBCL + Linux + например, библиотеки с http://common-lisp.net/project/cl-dwim/, то язык + платформа получаются достаточно мощные и удобные для использования.

Набор библиотек, конечно раздробляет сообщество, но ведь C++ как-то живёт с Qt, std, MSVC и ещё полудюжиной несовместимых реализаций, в которых даже строки по разному представлены... :-)

Ergo, Lisp лучше C++ как язык и как платформа, по сравнению с Java, .Net проигрывает как переносимая платформа, но языковых возможностей всё равно больше.

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

> А в С++
> list.find(key)->second - чтение

> list.find(key)->second = new_value


Я тебя, наверно, удивлю, но в c++ можно писать и list[key] для обоих случаев.
Первое время в языкам с не c-like синтаксисом раздражает отсутствие подобного сахарка. А потом понимаешь, что запись в виде [ dict get .. ], [ array get ... ], [ something get ... ] куда более единообразна.

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

>XML - это ущербный формат, который плохо читается и человеком, и машиной.

HTML это вообще просто ужас, спагетти из скобочек, знаков больше-меньше, равно, кавычек. Вообщем, мрак. Если читать html без браузера. Для XML тоже давно придумали и просмотрщики и редакторы и с валидацией и с код-комплитом и с посветкой и ...

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

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

Альтернатива есть? Назови ту платформу на которой и писать надо меньш из расчета "количество букв/смысл выражения", дабы как ты говоришь повысить производительность труда, и чтоб не было помойки с библиотеками, и чтоб реализации были свместимы тютелька в тютельку, и чтоб кроссплатформенность была во всем и всегда и т.д. Я таких языков/платформ не знаю и никгода о них не слышал.

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

Мое мнение очень простое: у лиспа есть приемущества, которые с лихвой перекывают перечислнные тобой недостатки. Надо уметь использовать язык, вот и все. Лисп как никакой другой язык позволяет все что угодно переделать под себя и как только ты это поймшь, так и большая часть перечисленный тобой якобы проблем отпадет сама собой.

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

> В С и подобных языках нужно сначала задекларировать тип переменной. Хотя можно вместо этого принять некие соглашения, позволящие писать polymorphicArray x = {1,"sdfasdf",new foo())} Это - большое ограничение на С- образные языки, которое мешает в работе.

ты просто с++ не знаешь, такое "соглашение" пишется в 20 строчек, я даже на ЛОРе постил такую программку

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

> лисп <...> Теперь болезнь запущена и я бы прописал этому языку эвтаназию. Из гуманизма.

согласен, хотя может какие-то идеи оттуда взять можно

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