Вопрос к Vlad2: Nemerle & R#
От: EvilChild Ниоткуда  
Дата: 22.03.06 20:52
Оценка:
Vlad2, ты тут очень увлекательно рассказывал о Nemerle (говорю без всякой иронии),
какие преимущества ты бы получил разрабатывая R# на Nemerle?
Та же самая функциональность могла бы быть достигнута меньшим объёмом кода?
Код был бы понятнее?
Код был бы надёжнее (менее подвержен ошибкам)?
Как бы изменились требования к памяти?
Изменились ли бы скростные характеристики кода?
Можно было бы уложиться в меньшие сроки разработки?
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re: Вопрос к Vlad2: Nemerle & R#
От: WolfHound  
Дата: 22.03.06 21:02
Оценка:
Здравствуйте, EvilChild, Вы писали:

Я не Влад но отвечу: Если есть Nemerle то R# не нужен. Ибо Nemerle может все что может R# при том намного проще и удобней.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[2]: Вопрос к Vlad2: Nemerle & R#
От: EvilChild Ниоткуда  
Дата: 22.03.06 21:07
Оценка:
Здравствуйте, WolfHound, Вы писали:

WH>Я не Влад но отвечу: Если есть Nemerle то R# не нужен. Ибо Nemerle может все что может R# при том намного проще и удобней.


R# взят просто как немаленький и достаточно сложный проект, который писал Vlad2, исходники которого доступны,
ну и ещё то, что Vlad2 главный евангелист Nemerle на rsdn, а то, что он не нужен при наличии Nemerle это понятно.
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Nemerle & R#
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.03.06 22:55
Оценка: 62 (5)
#Имя: FAQ.nemerle_and_r#
Здравствуйте, EvilChild, Вы писали:

EC>Vlad2,


VladD2, если можно.

EC> ты тут очень увлекательно рассказывал о Nemerle (говорю без всякой иронии),

какие преимущества ты бы получил разрабатывая R# на Nemerle?

Имея Nemerle нет смысла заниматься R#-ом. Так что если бы я встретил такой проект в то время, то просто не стал бы заниматься R#-ом.

Дело в том, что R# — это попытка добавить в близкий к идеальном императивный яызык средства метапрограммирования. Макросы Nemerle — это уже готовая система метапрограммирования. Причем она более законченная и целостная.

Так что на сегодня R# имеет только одно приемущество над Nemerle — полноую обратную совместимость с C# 2.0 (а в будующем, думаю, и 3.0).

В общем-то идеи Nemerle можно 1 в 1 переносить в R#. Та же система квази-цитирования — это то, что я постоянно искал. В купе с идеей метаатрибутов (до которой я дошел еще не зная о Nemerle) получается полноценное и очень удобное решение практически всех вопросов метапрограммирования.

EC>Та же самая функциональность могла бы быть достигнута меньшим объёмом кода?


Еще раз. Скорее всего R#-а бы просто небыло бы.

Лучше описать разницу в подходах, чем думать о том, как R# выглядел бы на Nemerle.

Итак, в системе метапрограммирования нужны три вещи:
1. Средства порождения нового кода. Таким средством в Nemerle является квази-цитирование. В R# приходилось возиться с AST, что приводило к довольно сложному и трудно изменяемому коду. С подачи Вольфхаунда я ввел возможноть помечать код и получать помеченные куски AST относительно простым образом, но все же это намного сложнее чем использование квази-цитирования.
2. Средства привязки к имеющемуся коду. Поясню... Метакод в системах типа R# и Nemerle не может жить сам по себе. Он должен или по модели генерировать конечный код, или модифицировать имеющийся код. Во втором случае нужна некая привязка к коду явлющемуся моделью (т.е. коду который нужно изменить с помощью метапрограммы). Я додумался до очевидной идеии использования атрибутов C#, но долго мучался, и так и не пришел к тому как удобнее всего привязывать метапрограммы к коду методов. Я думал, о интерпретации вызовов функций как о макросах, но это не стыковалось с идеей использования атрибутов. Я даже думал о том, чтобы ввести атрибуты для кода методов. Но это привело бы к несовместимости с C#. А этого я очень нехотел. В Nemerle поступили просто. Они ввели метаатрибуты и макросы в стиле функций. Это решило все проблемы.
3. Средство поиска по AST. В R# было использовано довольно красивое рещение которое в общем-то даже в чем-то более мощьное чем то, что используется в Nemerle. Таким рещением стало использование XPath. Мы реализовали движок XPath-запросов над AST и таким образом получили возможность осуществлять сложнейший поиск кусков AST подлежащих анализу или модификации. В Nemerle для этих же целей используется сопоставление с образцом (pattrn matching). Учитывая, то, что в качестве образца можно применять квази-цитирование, и то, что в оразце можно задавать "активные части", т.е. переменные — это явилось очень хорошим решением проблемы. Хотя XPath более гибок как язык запросов, но он является, то что Nemerle-овцы называют "строковым DSL-ем", и плохо интегрируется с основным языком (C#-ом). Отсюда периодически возникает необходимость довольно некулюжих приведений типов и невозможность котроля типов во время компиляции. Кроме того в XPath нет средств модификации данных, и код которому требуется менять AST выглядит довольно громоздко.
Сопоставление с образцом не имеет этих проблем, хотя и хуже выглядит в качестве средства поиска по AST (поиск получается более императивным и громоздким). Однако на практике в макросах Nemerle все выглядит довольно гормонично.

EC>Код был бы понятнее?


Квази-цитирование, гигиеничность, сопоставление с образцом точно позволили бы сделать код короче и понятнее. Но все эти средства в общем-то можно встроить в R#.

EC>Код был бы надёжнее (менее подвержен ошибкам)?


Более короткий и более понятный код всегда более надежен.

EC>Как бы изменились требования к памяти?


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

EC>Изменились ли бы скростные характеристики кода?


Они зависят от степени оптимизации. В R# и так оптимизаций было сделано очень не много. В основном алгоритмические. Так движок XPath-запросов был переписан с использованием генерации кода на основе иформации о типах, а потом и с использованием самого R#-а. Это дало резкое увеличение работы XPath-движка. Однако XPath-движек можно было бы оптимизировать и сильнее. Идеи в этой области были. Но из-за объема работа пока что они не реализованы. В принципе Nemerle позволил бы реализовать движок запросво проще и качественнее. Но и сам R# будучи доделанным повзолил бы это сделать.

EC>Можно было бы уложиться в меньшие сроки разработки?


Откровенно говоря сроки скорее зависят от наличия свободного времени и желания.
Учитывая, что время ресурс дорогой имея Nemerle просто небыло бы смысла ваять R#.


ЗЫ

Попробую объяснить почему я вообще занялся R#-ом.

Когда-то моим любимым языком был С++. Я перепробовал много чего, но из виденного мной он пожалуй был самым гибким и добным. Однако почти с самого начала я видел массу недостатков в нем. Глядя на Васик и Дельфи я понимал, что языку очень нехватает таких свойств как компонентности и типобезопасности (причем второе я скорее чувствовал чем понимал осознанно). В своих разработках мы даже применяли связку Васика и С++. На первом клепались контролы и бизнес-логика, а на С++ более системные библиотеки.

Когда появился C# я вдруг обнаружил, что этот язык намного совершенее С++ во многих обаластях. Однако кое чего в нем все же нехватало. Это было обобщенное программирование и метапрограммирование. Причем если обобщенное программирование в С++ было действительно на высоте, то метапрограммирование в нем было в ужаснейшом состоянии. Макросы приводили к куче опасных проблем и небыли полноценным языком программирования, а метапрограммирование на шаблонах попросу было реализовано на базе побочных эффектов и имело огромное количество проблем. По сути во времена когда я во всю программировал на С++ этого подхода просто небыло. Ведь метапрограммирование на шаблонах использует возможности котрых почти небыло в VC++ 5-6 которые я использовал.

Так вот обобщенное программирование появилось в C# 2.0, а вопрос с метопрограммированием как раз и был призван решить R#.

R# задумывался как расширение (надстройка) C# привносящее в него средства метапрограммирования. Nemerle же кроме очень логичной системы метапрограммирования привнес еще и средства фунционального программирования. Причем Nemerle позволяет выбирать парадигму более всего подходящую для решения задач. Этот язык реально реализовал лозунги которые только провозглашаются в C# и С++. Причем реализовал замечательно и не в ущерб другим возможностям.

Например, в Nemerle идиально реализуется идеи фикс о которой так любят твердить фанаты С++:
1. Зачем вводить в язык то, что реализуется библиотекой?
2. Язык должен включать только базовые вещи, а весь синтаксический сахар должен реализоваться в виде библиотек.
С++ реально содержит кучу того, что можно было бы реализовать в библиотеках и не предоставляет нужной функциональности.
При этом Nemerle обладает такими же компонентными возможностями как и C#.
И более того, он позволяет писать в функциональном стиле не хуже чем ML или Хаскель.

В общем, Nemerle — это отличная работа! И будет очень жаль если она пройдет мимо мэйнстрима. При должной раскрутке и "техническом оснащении" (поддержке IDE, наличии полноценной помощи, книг и т.п.) он может прочно и на долго занять место лидера среди мэйнстрим языков общего назначения. При этом Васик мог бы занять нишу языка для прикладников и "домохазяек", С/С++ нишу битодробилок, а Nemerle займет нишу котрую сейчас занимают C# и С++, т.е. языка общего назначения для решения нетривиальных задач.

Однако возможно, что Nemerle так и не станет лидером в жолтой майке, тогда его идеи можно будет хотя бы частично реализовать в R# и C#.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: Вопрос к Vlad2: Nemerle & R#
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.03.06 23:19
Оценка: 2 (1)
Здравствуйте, EvilChild, Вы писали:

EC>R# взят просто как немаленький и достаточно сложный проект, который писал Vlad2, исходники которого доступны,


Тогда пример плохой. R# скорее конкурент Nemerle, чем что-то что можно реализовать на Nemerle.

Скорее тут нужно прикинуть Nemerle на другие проекты. Попробую это сделать:
1. Rsdn.Editor. Этот проект практически на 90% базируется на ООП. Варианты Nemerle-а позволили бы сократить описание некоторых частей проекта. Например, они позволили бы сократить описание команд (т.е. реализации паттерна команда). Возможно кое-где Nemerle позволил бы избавиться от реализации паттернов. Но не думаю, что бщий объем кода уменшился бы сильнее чем процентов на 20%. Хотя это конечно только прикидки. Возможно, что-то я упускаю из вида.
2. Янус. Вот тут бы Nemerle мог оказать очень большой эффект. Взять хоят бы пример реструктуризатора на который у меня никак не получается выделить времни, чтобы его закончить. Одна из проблем реструктуризатора — генерация SQL-кода для разных диалектов SQL. Чтобы упростить эту задачу я воспользовался шаблонным движком StringTemplate. Например, вот как выглядит код создания индекса:
CreateIndex(name, table, isClustered, isUnique, entries) ::= <<
/* General:CreateIndex */
CREATE $Unique(isUnique)$ $Clustered(isClustered)$ INDEX $Quot(name)$ ON $Quot(table)$
(
  $entries:{ entry | $entry.Column$ $Direction(entry.IsAscending)$}; separator=",\n"$
)
>>

Выражения внутри баксов (символов "$") — это активные части шаблона. Они или преобразуют в текст некоторые переменные, или вызвают другие шаблоны, или применяют шаблоны к так называемым множественным атрибутам. Так "$Quot(name)$" приводит к тому, что вызывается шаблон Quot() которому передается значнеие параметра name внешенего шаблона. В итоге "$Quot(name)$" приводит к тому, что вместо этого кода выводится имя индекса хранящееся в параметре "name" причем значение помещается в ковычки. Выражение "$entries:Xxx()$" приводит к тому, что шаблон Xxx применяется ко всем элементам помещенным в entries (в примере использован безымянный шаблон "{ ... }").
Думаю, что те кто уже успел пописать на Nemerle догадались, что это очень похоже на активные строки в Nemerle (реализуемые макросами).
StringTemplate — это здоровая библиотека (объем ее кода сравним с объемом кода всего реструктуризацтора) не лишенная кучи недостатков. Так сообщения об ошибках в StringTemplate бывают крайне неинформативными, время затрачиваемое на загрузку шаблонов при запуске из под отладчика очень высокое, а возможности по расшерению не очень высокие (фактически библиотеку развивает только ее автор).
На Nemerle я мог бы создать встроенный в язык движек шаблонов лишенный практически всех нидостатков StringTemplate. При этом решение было бы быстрым (ведь пораждался бы код во время компиляции) и гибким (ведь я мог бы использовать всю мощь языка). При этом слжность реализации такого движка была бы куда ниже чем если это делать внучную.

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

Кстати, нехилым проектом доказывающим, что Nemerle мощьнейший язык является сам компилятор Nemerle. Он изначально является компонентом (реализован в виде ДЛЛ и может подгружаться динамически). Его код краток и понятен. Он задействует практически все свои возможности. Аналогичный проект на С++ был бы в десятки раз бльше. Да и на C# тоже намного больше.

EC>ну и ещё то, что Vlad2 главный евангелист Nemerle на rsdn, а то, что он не нужен при наличии Nemerle это понятно.


Да, я за него даже еще не брался. Мы еще шашочкой то помахаем.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[2]: Вопрос к Vlad2: Nemerle & R#
От: bigger longer and uncut  
Дата: 23.03.06 03:29
Оценка: 50 (8) :)
Здравствуйте, VladD2, Вы писали:

VD>И более того, он позволяет писать в функциональном стиле не хуже чем ML или Хаскель.


Ого, неслабое заявление.
Только необоснованное. Если взять Nemerle как _язык_, то он уступает и ML (особенно MetaML/Ocaml) и уж тем более хаскелю. ни такой развитой системы типов, ни контроля за редукционной стратегией (если я не упустил ничего) ни такого уровня формализма. Да первая же попытка написать какой-нибудь хитроумный комбинатор даст понять кто где.
А если взять компилятор немерля с этими на каждом шагу в кассу и не в кассу понапиханными макросами, так все еще хуже, как ни удивительно. Если кто-то несогласен, я с радостью услышу опровержение и рассказ как удобно на самом деле делать композицию из макроса и функции.
Кстати у common lisp'a та же проблема и даже после Scheme он часто вызывает лишь глухое раздражение, несмотря на более мощные макросы.

Да и сама по себе система макросов — сомнительная мегафича. Кроме того, что их выразительная мощь на самом деле сильно ограничена (самим фактом работы их на уровне AST и относительной их локальности и непредсказуемости — да, если они полны по-тьюрингу на них можно сделать все — но в какой-то момент сложность все равно сделает это бессмысленным), еще и сам по себе этот подход используется десятки лет и приделать макросистему к любому языку дело моментальное. Тем более что почти для любого языка уже готовых макродвижков как минимум дюжина. В Окамле даже встроенный есть. В хаскеле встроенных сразу три штуки на выбор.
Правда нужны они тому же хаскелю как собаке пятая нога — чем им заниматься в ленивом языке с каррингом — это нужно очень сильно думать, чтобы придумать. А когда придумаешь — тут-то они и бесполезны, т.к большинство таких задач сводятся к нетривиальной манипуляции с типами.
Потому если всерьез кому нужно реально что-то реально сложное, то используют term rewriting трансформацию. А вот здесь уже макросы ничем похвастаться не могут. MSP типа MetaOcaml еще как-то, но не макросы.

В общем конечно по сравнению с C# оно огого, но не боле.


VD>В общем, Nemerle — это отличная работа! И будет очень жаль если она пройдет мимо мэйнстрима. При должной раскрутке и "техническом оснащении" (поддержке IDE, наличии полноценной помощи, книг и т.п.) он может прочно и на долго занять место лидера среди мэйнстрим


Кстати если под IDE понимаются все эти рефакторинги и интеллисенсы — то в чем вообще смысл?
IDE как design-time metaprogramming явно и не имеет смысла и конфликтует с compile-time.
Причем где-где, а на этом уровне (вбитие километров повторяющегося кода и тп) макросы по возможностям кроют с лихвой.
Ну в самом деле — идеальный код не требует дублирования и необходимости сложной навигации просто в силу малой своей избыточности.
Макросы в общем для этого в основном и сделаны (ну еще, конечно, чтобы откладывать вычисления, например, но это мелочи по сравнению).
Формально это кстати очень просто обосновывается — во время compile-time в любом случае больше информации, чтобы оставлять работу кодогрузчику на уровне пользователя ну и следовательно таких же возможностей как раньше уже в IDE не получишь. В рантайме еще больше, потому и IDE для динамических языков — это обычно одно название.

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

VD>языков общего назначения. При этом Васик мог бы занять нишу языка для прикладников и "домохазяек", С/С++ нишу битодробилок, а Nemerle займет нишу котрую сейчас занимают C# и С++, т.е. языка общего назначения для решения нетривиальных задач.


Как-то сомневаюсь. Скорее к тому моменту, когда бренд Nemerle раскрутится, на дотнете можно станет пускать нормально окамл и хаскель и немерлю придется туговато. учитывая, что сейчас, например, большинство случаев отказа от них связано с отсутствием важных библиотек типа развивающегося и поддерживаемого гуя, а user- & codebase гораздо больше. Ну и еще один момент — дотнет — это вообще очень маленький сегмент всего IT и использовать языки, которые есть только на нем сильно менее целесообразно, чем те, что есть везде.
Ну и там для некоторых(большинства) нетривиальных задач как использовали пролог, лисп, APL и фортран, так и будут продолжать.
Ну по крайней мере пока некоторые не будут вытеснены монстрами а-ля Maude и ASF+SDF
***
Re[4]: Вопрос к Vlad2: Nemerle & R#
От: Andrei N.Sobchuck Украина www.smalltalk.ru
Дата: 23.03.06 07:55
Оценка:
Здравствуйте, VladD2, Вы писали:

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


Так всё таки, что мещает заимплементить его на N, и интегрировать со "старым" Янусом?
http://www.smalltalk.ru | << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Я ненавижу Hibernate
Автор: Andrei N.Sobchuck
Дата: 08.01.08
!
Re[5]: Вопрос к Vlad2: Nemerle & R#
От: VladD2 Российская Империя www.nemerle.org
Дата: 23.03.06 12:01
Оценка:
Здравствуйте, Andrei N.Sobchuck, Вы писали:

ANS>Так всё таки, что мещает заимплементить его на N, и интегрировать со "старым" Янусом?


Реструктуризатор или весь Янус?

Весь Янус переписывать не разумно. А реструктуризатор в принципе можно.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[6]: Вопрос к Vlad2: Nemerle & R#
От: Andrei N.Sobchuck Украина www.smalltalk.ru
Дата: 23.03.06 12:28
Оценка:
Здравствуйте, VladD2, Вы писали:

ANS>>Так всё таки, что мещает заимплементить его на N, и интегрировать со "старым" Янусом?


VD>Реструктуризатор или весь Янус?


Реструктуризатор.
http://www.smalltalk.ru | << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Я ненавижу Hibernate
Автор: Andrei N.Sobchuck
Дата: 08.01.08
!
Re[3]: Вопрос к Vlad2: Nemerle & R#
От: VladD2 Российская Империя www.nemerle.org
Дата: 23.03.06 14:32
Оценка: 98 (6) +1
Здравствуйте, bigger longer and uncut, Вы писали:

Ну, что же еще одно мнение законченного апологета ФЯ.
В общем-то особого смысла отвечать на него нет. Все равно столь сформировавшюся позицию не изменить.

Однако, я все же отвечу.
Ответ мой рассчитан на сомневающихся.

VD>>И более того, он позволяет писать в функциональном стиле не хуже чем ML или Хаскель.


BLA>Ого, неслабое заявление.

BLA>Только необоснованное.

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

BLA> Если взять Nemerle как _язык_, то он уступает и ML (особенно MetaML/Ocaml) и уж тем более хаскелю.


Это ничем не обоснованные заявления. Мое мнение — все что ужно длоя удобного программирования в функциональном стиле в нем есть. Но с удовольствием послушаю аргументированное доказательство обратного. Все же Ocaml и Хаскель я знаю очень поверхностно.

BLA> ни такой развитой системы типов,


Заявление громкое, необоснованное и крайне сомнительное.

BLA> ни контроля за редукционной стратегией (если я не упустил ничего)


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

BLA> ни такого уровня формализма.


Очень убедительно. С такими аргументами в лес.

BLA> Да первая же попытка написать какой-нибудь хитроумный комбинатор даст понять кто где.


Ну, дык зачем дело встало?

К тому же ты кое-чего недопонимаешь. У 99% народа нет, нужды писать комбинаторы (хотя это на Nemerle делать можно). Людям нужно удобно и просто писать нужные им код, решать их задачи.

И тут кроется главный вопрос. Люди уже в массе своей не хотят использовать чисто функциональные языки типа Хаскель. Более того гибридные языки типа Окамла им тоже мало интересны. Это факт, который очень легко доказать. Надо доказывать?

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


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

Апеллировать к возгласам вроде "в кассу понапиханными макросами, так все еще хуже, как ни удивительно..." бессмысленно и не интересно.

BLA>Кстати у common lisp'a та же проблема и даже после Scheme он часто вызывает лишь глухое раздражение, несмотря на более мощные макросы.


Какая такая же? Может быть сначала нужно доказать, что проблема вообще есть?

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

Что касается макросов Nemerle-а, то как раз они намного ближе к макросам Схемы нежели Лиспа (хотя, по сути, Схема — это клон Лиспа, но как раз подсистема макросов в нем сильно отличается).
Надо понимать, что авторы Нэмерла знают как минимум не меньше тебя в этом вопросе. В конце вот этого http://nemerle.org/metaprogramming.pdf документа есть раздел "Related work". В нем кратко описывается, откуда растут ноги макросов Немерла, и почему были выбраны те или иные решения.

Вот что там сказано по поводу макросов Сехемы:

10.1 Гигиеничные макросы Scheme

У нашей системы много общего с современными макрорасширениями Scheme[1]:
• Альфа-переименование и связывание переменных выполняется после развертывания макроса, с использованием контекста, хранимого в макросе.
• Макросы могут контролируемо использовать внешние имена, не боясь пересечься с посторонними именами.
• Сторона, на которой вызывается макрос, не использует какого-либо особого синтаксиса для вызова макросов, единственное место, где используется особый синтаксис – определение макроса, что обуславливает легкость использования макросов программистами, несведущими в метапрограммировании.
Поддерживая перечисленное выше, мы встроили систему макросов в статически типизированный язык. Типы в сгенерированном коде проверяется после раскрытия. Мы также обеспечиваем четкое разделение этапов – метафункции до использования должны быть скомпилированы и сохранены в библиотеке.
Работа над Scheme длилась довольно долго, и предлагалось много интересных вещей. Например, макросы первого класса в [9], кажется, можно реализовать в Nemerle с помощью простой передачи функций, оперирующих кодом объектов.


Другими словами, как раз со Схемы и были взяты многие идеи макросов немерла.

BLA>Да и сама по себе система макросов — сомнительная мегафича.


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

BLA> Кроме того, что их выразительная мощь на самом деле сильно ограничена (самим фактом работы их на уровне AST и относительной их локальности и непредсказуемости — да,


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

BLA>если они полны по-тьюрингу на них можно сделать все


Они полны по Тьюрингу.

BLA> — но в какой-то момент сложность все равно сделает это бессмысленным),


На каком-то безусловно. На каком-то уровне сложности все современные средства созданные человечеством бессильны. Ну и что?

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

BLA>... еще и сам по себе этот подход используется десятки лет


Да, используется. Не спорю. Но используется в языках, которые по тем или иным причинам не стали и вряд ли когда-нибудь станут действительно популярными. Nemerle же имеет все предпосылки стать популярным. Он не напичкан догмами. Как и С++ он предоставляет выбор парадигмы. Причем делает это куда эффективнее и чише чем С++. Функциональное программирование на Немерле — это функциональное программирование. Без компромиссов, моря обвязочного кода и ужимок свойственных С++. Императивное программирование хотя и практически целиком встроено на макросах, но все же выглядит очень естественно. Даже известные апологеты C#/С++ находят императивную составляющую в Немерле очень достойно реализованной.

BLA> и приделать макросистему к любому языку дело моментальное.


Ага. Языком. Я вот пытался сделать это для C# и могу сказать, что это не самая простая задача. Она конечно реально, но есть две проблемы. Первое — нужно иметь четкое видение того как это сделать с учетом особенностей языка. Второе — это просто большой объем работы. Даже банальные вещи вроде совместимости с языком в который встраиваются макросы и интуитивность использования являются очень немалыми проблемами. На сегодня языки обладающие действительно мольными, удобными, гибкими и совместимыми с разными парадигмами подсистемами макросов можно перечислить по пальцам одной руки. И, по-моему, Немерле лидер среди них. По крайней мере, аналогичной реализации у императивных языков я вообще не видел.

BLA> Тем более что почти для любого языка уже готовых макродвижков как минимум дюжина.


Громкие слова не имеющие ничего общего с действительностью. К примеру, перечисли эти дюжины для C# и С++.

BLA> В Окамле даже встроенный есть.


Это не правда. Для Окамла есть только препроцессор CamlP4. Вот слова о нем из привденного выше документа:

10.4 CamlP4

CamlP4 [12] – это препроцессор для OCaml. Его LL(1)-парсер — полностью динамический, что позволяет выразить весьма сложные расширения грамматики. Макросы (именуемые расширениями синтаксиса) должны быть скомпилированы и загружены в парсер до использования. При работе они могут конструировать новые выражения (используя систему цитирования), но только на уровне нетипизированного дерева разбора. Более углубленное взаимодействие с компилятором невозможно.


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

BLA>В хаскеле встроенных сразу три штуки на выбор.


Опять не правда. Есть экспериментальные расширения Хаскеля предоставляющие такие возможности. Лучший из них — Template Haskell и послужил одним из прототипом для макросов Немерла:

10.2 Template Haskell

Между макросами Template Haskell [2] и Nemerle есть интересные различия:
• Разрешение связываний при трансляции цитирования дает возможность сделать вывод о корректности типов объектного кода до его использования. Это позволяет значительно раньше обнаруживать ошибки. Но наличие splicing-конструкции $ делает типизацию отложенной до следующего этапа компиляции, и в этом случае новые связывания должны быть динамическими.
• Макросы Template Haskell, как и любая другая функция Haskell, являются функциями высшего порядка: их можно передавать как аргументы, применять частично и т.д. Это, однако, требует вручную помечать, какой код должен исполняться при компиляции. Мы решили позволить вызывать макросы просто по имени (как в Scheme), так что их использование выглядит как вызов обычной функции. Вы по-прежнему можете использовать функции высшего порядка (функции, оперирующие объектным кодом, могут быть произвольными), но только верхние метафункции (предваряемые macro) запускают вычисления во время компиляции.
• Мы не ограничиваем splicing объявлений с кодом верхнего уровня и не вводим особого синтаксиса для вводящих их макросов. Это кажется хорошим способом использования преимуществ связывания имен после раскрытия макроса и императивного стиля, присущего Nemerle. Для императивного программиста естественно думать о вводимых определениях как о побочных эффектах вызова макросов, даже если эти вызовы находятся в цитируемом коде.
• Мы вводим макросы, оперирующие с типами, объявляемыми в программе, и способные императивно изменять их. Более того, они выглядят как атрибуты, применяемые к определениям типов, так что опять же программисту не обязательно знать что-нибудь о метапрограммировании, чтобы использовать их.
Есть еще много сходств с Template Haskell. Мы напрямую позаимствовали оттуда идею квази-цитирования и splicing-а. Идеи исполнения функций при компиляции и отложенной проверки типов также навеяна Template Haskell.


BLA>Правда нужны они тому же хаскелю как собаке пятая нога — чем им заниматься в ленивом языке с каррингом — это нужно очень сильно думать, чтобы придумать.


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

BLA> А когда придумаешь — тут-то они и бесполезны, т.к большинство таких задач сводятся к нетривиальной манипуляции с типами.


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

BLA>Потому если всерьез кому нужно реально что-то реально сложное, то используют term rewriting трансформацию. А вот здесь уже макросы ничем похвастаться не могут. MSP типа MetaOcaml еще как-то, но не макросы.


Хм. Сдается мне, то эти слова просто демонстрируют то, что ты не понимаешь, что такое макросы Немерла.

Вот что сказано о MetaOCaml на титульной странице его сайта:
http://www.metaocaml.org/

MetaOCaml is a compiled dialect of MetaML.

А вот, что сказано о MetaML в упомянутом мной выше документе:

10.6 MetaML

MetaML [7] вдохновил и Template Haskell и MacroML, введя квази-цитирование и идею типизация объектного кода. Он был разработан в основном для операций с кодом и его исполнения в рантайме, так что это несколько отличающаяся от нашей область деятельности.

И о MacroML, так как без слов о нем картина не будет ясна:

10.5 MacroML

В MacroML [6] было предложено использовать макросы времени компиляции для языка ML. Это имеет много общего с Template Haskell в смысле связывания имен в цитировании до раскрытия макросов. MacroML, кроме того, позволяет захватывать символы в месте применения макроса (это похоже на нашу функцию UseSiteSymbol()). И все это производится без необходимости отказываться от типизации цитат.
Макросы в MacroML ограничены конструированием кода из имеющихся частей, поиск декомпозиция и кода невозможны.


BLA>В общем конечно по сравнению с C# оно огого, но не боле.


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

Ну, а лично я полностью уверен, что Неперле превосходит Окамл и Хаскель. Как минимум Немерле значительно удобнее если рассматривать его как статически-типизированный, типобезопасный, объектно-ориентированный язык. Ведь ОО-возможности в нем позаимствованы из лидеров в этой области среди мэйнстрим языков (C#, Ява, С++).

VD>>В общем, Nemerle — это отличная работа! И будет очень жаль если она пройдет мимо мэйнстрима. При должной раскрутке и "техническом оснащении" (поддержке IDE, наличии полноценной помощи, книг и т.п.) он может прочно и на долго занять место лидера среди мэйнстрим


BLA>Кстати если под IDE понимаются все эти рефакторинги и интеллисенсы — то в чем вообще смысл?


Это отдельный вопрос. Мне вобщем-то окровенено мало интересно обсуждение этого вопроса с теми кто не видит нужны в IDE, интелисенсе и рефакторинге, так как лично я испытываю потребность в этих возможностях просто таки на чисто животном, интуитивном уровне. Такой спор для меня аналогичен спору на тему "нужен ли лифт в 16-ти этажном доме". Это просто очень удобно!

BLA>IDE как design-time metaprogramming явно и не имеет смысла и конфликтует с compile-time.


От IDE в первую очередь мне нужны средства ускоряющие написание, отладку и рефакторинг кода. Метапрограммирование тут как бы вовсе не причем. Хотя кое что из метапрограммирования мне в IDE тоже не помешала бы. Например, к оным можно отнести всякого рода дизайнеры. Так мне очень нравится изучать иерархию классов в дизайнере классов (если кто не видел оный в SV2005, то ближайшим аналогом будут UML-дизайнеры, хотя они несколько отличаются), а так же нравится пользоваться GUI-дизайренами.

BLA>Причем где-где, а на этом уровне (вбитие километров повторяющегося кода и тп) макросы по возможностям кроют с лихвой.


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

К тому же у интелисенса есть еще ряд премуществ. Одно из важнейших — это отсуствие необходимости сокращать названия идентификаторов. Плохая читабельность кода на Хаскеле и других ФЯ зачастую связанна с банальным пренебрежением к качеству и осмысленности идентификаторов. Это же повышает и сложность обучения. Ведь запоминать традиции вроде x::xs или даже h::t — это отдельный и не малый труд. И мне жаль тех апологетов ФЯ которые не понимают этого просто потому, что сами уже прошли через это.

BLA>Ну в самом деле — идеальный код не требует дублирования и необходимости сложной навигации просто в силу малой своей избыточности.


Хм. Эти слова сомнительны сразу по двум причинам.
1. Идиальный код — это то к чему стремятся хорошие программисты. Тут сразу два ключевых слова. Стремятся и хорошие. Между тем не всегда удается написать идеальный код. Причем "не всегда" — это слова про хороших программистов. Начинающие же и плохие программисты создают идеальный код вообще очень редко. Так что возможности по навигации и рефакторингу нужных хотя бы для того, чтобы превращать не идеальный код в тот, что ближе к идеалу. Забавно, что этот процесс рекурсивен по своей природе. Один рефакторинг может привести к осознанию того, что нужен еще один. Да и со временем отношение к коду может измениться.
2. Код может быть большим не только из-за того, что он не идеален. Код банально может быть слишком объемным вследствие сложности решаемой задачи. Несомненно, грамотная декомпозиция способна сделать отдельные его участки простыми и понятными, но, черт побери, декомпозиция только увеличивает объем кода! Рано или поздно мы приходим к тому, объем проекта столь велик, что в нем становится сложно разораться не только без достойных средств навигаций, но и без средств визуализации вроде дизайнеров классов.

Я замечал, что апологеты ФЯ часто с пренебрежением относятся к данным вопросам, но мне кажется, что это их заблуждение. И сформировано оно возможно оттого, что они реально не решали с помощью своих любимых инструментов действительно объемных задач. ФЯ часто появляется где-то рядом с математикой или синтаксическим анализом. В этих областях функциональная декомпозиция, поднятая на высоких уровень в ФЯ действительно дает хороший эффект, но эти задачи не являются действительно объемными и легко делятся на относительно небольшие подзадачи. Связанность таких задач не очень высока. Между тем банальные примитивные финансовые программы приводят к огромным массивам тесно связанного кода. И в этих областях не использовать средства предоставляемые современными IDE — просто не размуно. Это все равно что добровольно вешать на себя гандикап.

BLA>Макросы в общем для этого в основном и сделаны (ну еще, конечно, чтобы откладывать вычисления, например, но это мелочи по сравнению).

BLA>Формально это кстати очень просто обосновывается — во время compile-time в любом случае больше информации, чтобы оставлять работу кодогрузчику на уровне пользователя ну и следовательно таких же возможностей как раньше уже в IDE не получишь. В рантайме еще больше, потому и IDE для динамических языков — это обычно одно название.

BLA>Ну я вообще к тому, что аутлайн, фолдинг, подсветка и replace c регекспами есть везде, а большего на метауровне и ненужно. А то лишь когнитивный диссонанс получается.


Однако "когнитивный диссонанс" звучит красиво. Хотя и совершенно не ясно о чем речь.

Отступы подсветка и replace — это минимум. Причем совершенно не достаточный для большинства людей привыкших полноценным IDE. Я не хочу спорить с тобой. Тебе может это и не надо. Но ты в меньшинстве. Заведи голосование на этом сайте и убедишься в этом.

VD>>языков общего назначения. При этом Васик мог бы занять нишу языка для прикладников и "домохазяек", С/С++ нишу битодробилок, а Nemerle займет нишу котрую сейчас занимают C# и С++, т.е. языка общего назначения для решения нетривиальных задач.


BLA>Как-то сомневаюсь. Скорее к тому моменту, когда бренд Nemerle раскрутится, на дотнете можно станет пускать нормально окамл и хаскель и немерлю придется туговато.


Ты видимо очень долго спал. И Окамл, и Хаскель давно прекрасно работают на дотнете. Вот тебе список ссылочек:
Haskell
Hugs98 for .NET
Haskell for .NET (using Mondrain for .NET) (Nigel Perry)
Haskell.net Project
Caml
F# (ML and Caml)
OCAMIL (Emmanuel Chailloux &amp; Raphael.Montelatici)

А вот более полный список языков:
http://www.dotnetpowered.com/languages.aspx

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

BLA>учитывая, что сейчас, например, большинство случаев отказа от них связано с отсутствием важных библиотек типа развивающегося и поддерживаемого гуя, а user- & codebase гораздо больше.


Ну, так какие там проблемы с библиотеками для вышеперечисленных языков?
Надо уметь смотреть правде в глаза. Языки вроде Окамла и Хаскеля просто не принимаются большинством программистов. Их любят только те, кто окончательно и бесповоротно проникся идеями ФЯ. Хаскель отпугивает своими манадами, полной ленивостью, отсутствием императивных конструкций и шифровальным стилем записи. Окамл кривой поддержкой ООП, отсутствием компонентности, непривычным синтаксисом. Схема и Лисп пугают тем, что нужно писать программы в АСТ.

Мне лично все равно будут ли апологеты ФЯ считать это фобиями, но это факт. Мэйнстрим не принял и врде ли примет большинство ФЯ.

Немерле же по сути являясь ФЯ умудряется достойно поддерживать и другие парадигмы. Даже в стиле старого доброго С на нем пишется без проблем.

BLA> Ну и еще один момент — дотнет — это вообще очень маленький сегмент всего IT и использовать языки, которые есть только на нем сильно менее целесообразно, чем те, что есть везде.


Кому как. Есть мнение, что управляемые среды вроде дотнета и Явы — это будущее программирования. Но это опять же отдельная тема, поднимавшаяся здесь не раз.

BLA>Ну и там для некоторых(большинства) нетривиальных задач как использовали пролог, лисп, APL и фортран, так и будут продолжать.


Для решения большинства задач, в том числе и не тривиальных, сегодня используются С++, Ява и C#. Это факт. Как раз Пролог и даже Лисп являются скорее исключением. Это языки используемые в узких нишах. Обычно в научных кругах. Я же говорю о Немерле как о претенденте на лидерство в области промышленного программирования.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[4]: Вопрос к Vlad2: Nemerle & R#
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 23.03.06 15:02
Оценка: +2
Здравствуйте, VladD2, Вы писали:

VD>Все же Ocaml и Хаскель я знаю очень поверхностно.


VD>Ну, а лично я полностью уверен, что Неперле превосходит Окамл и Хаскель. Как минимум Немерле значительно удобнее если рассматривать его как статически-типизированный, типобезопасный, объектно-ориентированный язык.


Довольно противоречивые высказывания однако. С учетом того, что OCaml (насколько я наслышан) как раз статически-типизированный и типобезопасный.


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re[5]: Вопрос к Vlad2: Nemerle & R#
От: VladD2 Российская Империя www.nemerle.org
Дата: 23.03.06 15:09
Оценка:
Здравствуйте, eao197, Вы писали:

E>Довольно противоречивые высказывания однако. С учетом того, что OCaml (насколько я наслышан) как раз статически-типизированный и типобезопасный.


Выделю ключевые слова:

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

... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[6]: Вопрос к Vlad2: Nemerle & R#
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 23.03.06 15:20
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>

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




Если вспомнить про то, что OCaml -- это Objective Caml и посмотреть на Chapter 3 Objects in Caml, то в твой фразе жирным придется выделить только вот это:

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


Поскольку аргументы про типизацию и объектность к OCaml-у не относятся.



Кстати, забавную ты описку сделал: 'Неперле'
Как бы после такого массированного промоушена Nemerle к нему эта кличка не приклеилась


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re[7]: Вопрос к Vlad2: Nemerle & R#
От: VladD2 Российская Империя www.nemerle.org
Дата: 23.03.06 15:53
Оценка:
Здравствуйте, eao197, Вы писали:

E>Если вспомнить про то, что OCaml -- это Objective Caml и посмотреть на Chapter 3 Objects in Caml, то в твой фразе жирным придется выделить только вот это:


E>

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


Я уже все написал все в исходном сообщении. Я считаю реализацию ООП в Окале неудобной.

Если ты считашь иначе, то выбрасывай свой любимый С++ на и перебирайся на Окамл.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[8]: Вопрос к Vlad2: Nemerle & R#
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 23.03.06 16:06
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Я уже все написал все в исходном сообщении. Я считаю реализацию ООП в Окале неудобной.


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

VD>Если ты считашь иначе, то выбрасывай свой любимый С++ на и перебирайся на Окамл.


Кстати, это не так уж маловероятно, как ты думаешь. Я бы сам хотел перейти на более современный язык, чем C++, лишенный тяжелого наследия C. Объектно-ориентированный, кроссплатформенный, быстрый, OpenSource и не принадлежащий какой-нибудь корпорации. Пока всерьез присматривался к D. А вот про OCaml забыл. Спасибо, что напомнил.


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re[9]: Вопрос к Vlad2: Nemerle & R#
От: IT Россия linq2db.com
Дата: 23.03.06 16:18
Оценка:
Здравствуйте, eao197, Вы писали:

VD>>Я уже все написал все в исходном сообщении. Я считаю реализацию ООП в Окале неудобной.


E>Так вот я и хочу тебе показать, что подобные утвержения мало чего стоят из-за твоих же слов: "Все же Ocaml и Хаскель я знаю очень поверхностно." Вряд ли поверхностные знания могут позволять считать что-либо удобным или неудобным.


Знания чего, Хаскеля или ООП? Я вот например знаю джаву очень поверхностно, но считаю отсутствие свойсв и принятые в мире джавы соглашения по именованию неудобными. Что не так в моём утверждении?
Если нам не помогут, то мы тоже никого не пощадим.
Re[10]: Вопрос к Vlad2: Nemerle & R#
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 23.03.06 16:23
Оценка: +1 -1
Здравствуйте, IT, Вы писали:

IT>Знания чего, Хаскеля или ООП? Я вот например знаю джаву очень поверхностно, но считаю отсутствие свойсв и принятые в мире джавы соглашения по именованию неудобными. Что не так в моём утверждении?


Знания OCaml-а. Влад противопоставляет Nemerle OCaml-у и высказывает свои оценки по OCaml-у не владея самим OCaml-ом. Именно это мне не нравится.

Твой же пример с Java в данном случае мне кажется неудачным.


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re[4]: Вопрос к Vlad2: Nemerle & R#
От: bigger longer and uncut  
Дата: 23.03.06 16:26
Оценка: +2 -13 :)))
Здравствуйте, VladD2, Вы писали:

VD>Ну, что же еще одно мнение законченного апологета ФЯ.


По-моему, это и то что ниже — это хамство конченного неуча.
Я даже не подумаю отвечать на весь этот агрессивный "слышал звон".
Посоветую только подучиться что ли.
ну там что такое "функциональный стиль" и чем он отличается от хаскеля и окамла, что такое типы и типобезопасный (немерль как типобезопасный язык меня особенно повеселил), что такое currying и term rewriting.
Да и вообще — выучить чтоли те же хаскель, окамл схему и коммон лисп, чтобы уже понимать о чем говоришь.

И поменьше слов вроде "апологет" — это из лексикона продавщиц пива.

превед
***
от модератора
От: WolfHound  
Дата: 23.03.06 16:37
Оценка:
Здравствуйте, bigger longer and uncut, Вы писали:

BLA>превед

За падонковщину на этом сайте банят.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[5]: Вопрос к Vlad2: Nemerle & R#
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 23.03.06 16:41
Оценка: 27 (1) +4 :))) :)
Интересно, почему наиболее агрессивные и неадекватные участники 'Философии программирования' в последнее время (reductor, Winnie Poh, теперь вот г.Необрезанный) оказываются приверженцами ФЯ? Это что не с проста? Что первично: ФЯ так крышу сносит или же безбашенные экстремалы находят для себя ФЯ в качестве любимой полянки для отдыха?


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.