Изучаем макросы Nemerle
От: VladD2 Российская Империя www.nemerle.org
Дата: 18.02.06 16:45
Оценка: 180 (16)
Единственный способ развеить скепсис — это попробовать.

Я решил попробовать макросы Nemerle в более-менее реальной задаче. Цель две.
1. Изучить собственно Nemerle и его макросы.
2. Продемонстрировать его возможности на этом форуме.

Я планирую несколько сообщений которые будут являться подсообщениями этого.

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

Итак, для экспериментов вам понадобится:
1. .NET Framework 2.0 (и возможно SDK). Лучше конечно если на машине просто установлена VS 2005.
2. Компилятор Nemerle и сопутствующая ему байда. Все это можно взять на их сайте http://nemerle.org. Так здесь http://nemerle.org/download/msi/nemerle-0.9.2.msi лежит инсталлятор для Виндовс. А здесь http://nemerle.org/download/ можно взять более свежую рабочую версию причем вместе с исходниками. Очень советую это сделать даже если вы выберете инсталляцию msi-я, так как поглядеть на исходники макросво и вообще на исподники созданные авторами языка очень полезно. Полноценной документации ведь пока нет, а исходники говорят о многом.
2. Сцинтила или другой редактор который упростить ввод и тестирование кода. Сцентилу можно взять здесь: http://prdownloads.sourceforge.net/scintilla/wscite167.zip?use_mirror=heanet
Файлы для обеспечения подсветки синтаксиса Nemerle для Сцинтылы можно взять здесь:
http://nemerle.org/svn/nemerle/trunk/misc/scintilla/SciTEGlobal.properties
http://nemerle.org/svn/nemerle/trunk/misc/scintilla/nemerle.properties
их нужно скопировать в каталог где лежат другие properties-файлы Сцинтилы.
3. Для упрощения компиляции и запуска файлов я написал простенький cmd-файлик для ХРюши:
@echo off

SET FileName=%1

SET MacroOutFileName=%FileName%-macro.dll
SET MacroSourceFileName=%FileName%-macro.n

SET SourceFileName=%FileName%.n
SET OutFileName=%FileName%.exe

if exist %MacroSourceFileName% (
  @echo --# Compiling Macro-assembly #---
  @echo ---------------------------------
  ncc.exe -no-color -debug+ -r Nemerle.Compiler.dll -t:dll %MacroSourceFileName% -out %MacroOutFileName%
  if not errorlevel 1 (
    @echo --- Compiling target assembly ---
    @echo ---------------------------------
    ncc.exe -no-color  -debug+ -r %MacroOutFileName% -t exe %SourceFileName% -o %OutFileName%
    rem -r System.Windows.Forms -r System.Data 
    if errorlevel 1 (
      @echo -------------------------------------
      @echo !!! Error detected in targer code !!!
    ) else (
      @echo --------------- OK -----------------
      @echo --Run: %OutFileName%
      @echo .
      %OutFileName%
    )
  ) else (
    @echo ------------------------------------
    @echo !!! Error detected in macro-code !!!
  )
) else (
  @echo ----- No Macro-assembly found ------
  @echo ------------------------------------
  if not errorlevel 1 (
    @echo --- Compiling target assembly ---
    @echo ---------------------------------
    ncc.exe -no-color  -debug+ -t exe %SourceFileName% -o %OutFileName%
    rem -r System.Windows.Forms -r System.Data 
    if errorlevel 1 (
      @echo -------------------------------------
      @echo !!! Error detected in targer code !!!
    ) else (
      @echo --------------- OK -----------------
      @echo --- Run: %OutFileName%
      @echo .
      %OutFileName%
    )
  ) else (
    @echo ------------------------------------
    @echo --! Error detected in macro-code !--
  )
)

Его нужно сохранить под именеме build-and-run.cmd в каталог где лежат бинарники Нэмерла (файл ncc.exe и т.п.).
Далее нужно отредактировать файл nemerle.properties добавив в него примерно такие строчки:
#Extra tool: Build With Macro and Run
#Build macro and target for console application"
command.name.6.*.n=Build With Macro and Run
command.6.*.n=build-and-run.cmd $(FileName)
command.6.subsystem.*.n=0
command.save.before.6.*.n=1
command.shortcut.6.*.n=F5

При этом, если что, нужно или изменить F5 на удобную для себя кнопку, или убрать/изменить аналогичный шорткат у имеющегся в nemerle.properties пункта.

Теперь открыв в Сцинтиле файл с расширением .n вы можете просто нажатием на F5 скомпилировать его и запустить на выполнение.
Если при этом рядом с компилируемым файлом будет лежать файл начальная часть имени которого совпадает с компилируемым, и оно оканчивается на «-macro», то сначала будет произведена компиляция этого файла. А потом, вслучае успеха будет откомплирован вайл без суффикса «–macro». Причем при его компиляции будет подключаться макросборка получившаяся на первом этапе. Например, если имеются файлы:
test-001.n
test-001-macro.n

если активизировать в Сцинтиле файл test-001.n и нажать F5, то будет сначала произвдена компиляция макросборки test-001-macro.dll (на базе файла test-001-macro.n), а потом будет произведена компиляция сборки test-001.exe (на базе файла test-001.n). Причем при компиляции test-001.exe будет использована макро-сборк полученная на первом этапе.
Если все скомпилируется, то будет произведен запуск test-001.exe. Иначе будет выданы сообщения об ошибке.

Для того, чтобы убедиться, что все работает создайте простенькую тестовую пару файлов:
Test-001.n – содержащий следующий код:
// abstract, and, array, as, base, catch, class, def, delegate, do, else, enum, event, extern, false, finally, for, foreach, fun, if, implements, in, interface, internal, lock, macro, match, module, mutable, namespace, new, null, out, override, params,  
// WriteLine public private protected internal

TestMacro();

Примечание: Коментарии с лабудой нужны для того, чтобы можно было пользоваться недо-интелисенсом. Если в Сцинтиле написат первые буквы слова и нажать Ctrl+Enter, то она выдаст список слов начинающихся на эти буквы.


И файл test-001-macro.n содержащий следующий код:
using System.Console;
// abstract, and, array, as, base, catch, class, def, delegate, do, else, enum, event, extern, false, finally, for, foreach, fun, if, implements, in, interface, internal, lock, macro, match, module, mutable, namespace, new, null, out, override, params,  
// WriteLine public private protected internal

macro TestMacro()
{
  WriteLine("compile-time\n");
  <[ WriteLine("run-time\n") ]>;
}

Теперь откройте Сцинтилой файл Test-001.n и нажмите F5.
Если в ответ вы увидите следующее:
>build-and-run.cmd test-001
--# Compiling Macro-assembly #---
---------------------------------
--- Compiling target assembly ---
---------------------------------
compile-time

--------------- OK -----------------
--Run: test-001.exe
.
run-time

>Exit code: 0

Значит вы все сделали верно и первый этап знакомства с Нэмерлом и его макросами пройдет.

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

Теперь прокомментирую, что вы видите на экране. Вывод:
---------------------------------
--- Compiling target assembly ---
---------------------------------
compile-time

Означает что началась компиляция основной сборки (сборки которую мы будем запускать на исполнение) и вызвался макрос. Который вывел информацию о себе на констоль. Надпись:
run-time

Ввел код сгенерированный макросом. Если вы теперь откроете полученный исполнимый файл Рефлектором, то увидите, что в функции Main() присутствует вызов:
Console.WriteLine("run-time\n");

а от макроса не осталось и следа. Это и есть чудесное действие макросов.

Продолжение следует.
... << RSDN@Home 1.2.0 alpha rev. 637>>

14.03.06 11:09: Перенесено из 'Философия программирования'
30.01.07 18:23: Перенесено модератором из 'Декларативное программирование' — IT
http://nemerle.org/Banners/?g=dark
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
01 Изучаем макросы Nemerle - Квази-цитирование
От: VladD2 Российская Империя www.nemerle.org
Дата: 18.02.06 20:14
Оценка: 156 (19)
Итак, сейчас я расскажу, что такое квази-циритвание (quasi-quotation).

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

Прежде чем разбираться с тем, что такое квази-цитирование давайте сначала разберемся, что вообще означает термин «цитирование».

Цитирование (quotation)

Компилятор преобразует текст программы сначала в список токенов (умные ученые мужи еще называют их терминалами), а потом в так называемое абстрактное синтаксическое дерево (Abstract Syntax Tree, AST). AST – это дерево состоящее из объектов описывающих код.
В AST каждый элемент синтаксиса представлен веткой AST-дерева. В общем-то когда программист воспринимает код, то он тоже мысленно строит подобное дерево.
Я не специалист в AST Nemerle-a, так что продемонстрирую AST на базе AST R#-а. Вот как выглядит вот такой кусок кода:
if (a == 1)
  a = 2;

в AST R#-а:
RStatement statement = new RConditionStatement(new RBinaryOperatorExpression(
    new RUnresolvedReferenceExpression("a"), 
    RBinaryOperator.IdentityEquality, new RPrimitiveExpression("1")),
    new RExpressionStatement(new RAssignmentExpression(
    new RUnresolvedReferenceExpression("a"), RAssignmentOperator.Assign,
    new RPrimitiveExpression("1"))));

Переменная statement будет содержать AST-векту описывающую if.
Если теперь вызвать у statement метод ToString():
Console.WriteLine(statement.ToString())

то на консоль выведется текст:
if (a == 1)
  a = 2;

«Зачем такие сложности?» – спросят многие. А затем, что AST является объектной моделью с которой намного удобнее работать программно нежели с плоским текстом.
Преобразовав текст программы в AST компилятор выполняет над AST множество действий. Так он может преобразовать AST некоторой высокоуровневой конструкции вроде foreach в более низкоуровневую (например, в while). Так же компилятор вычисляет множество семантических атрибутов. Так он вычисляет типы переменных и выражений. Производит их сопоставление и контроль. В общем, творит с AST все что хочет. В итоге компилятор преобразует AST в промежуточное представление (например, в MSIL), а затем и в машинный код.

Зачем я рассказал обо все этом, спросите вы?
А затем, что цитирование (quotation) – это способ заставить компилятор преобразовать некоторый код в это самое AST. Мы конечно могли бы просто написать код создающий AST (если бы компилятор предоставлял бы нам доступ хотя бы к нему), но это, как вы могли заметить не очень приятное занятие.
С использованием цитирования мы можем резко упростить данный процесс.
Вот как будет выглядеть получение AST приведенного выше выражения (if) с использованием цитирования:
RStatement statement = <[
    if (a == 1)
        a = 2; ]>;

Не правда ли, значительно проще? Это синтаксис C#. Вернее гипотетического C#. C# в котором поддерживается цитирование. А вот как тоже самое выглядит на Nemerle:
def expr = <[
    when (a == 1)
        a = 2; ]>;

Как видите, на Nemerle это выглядит даже проще (что не может не радовать ).
Я использовал имя expr, так как в Nemerle if-это не предложение (statement) как в C#, а выражение (expression).
В отличии от C# мне не пришлось указывать тип переменной. Это можно благодаря тому, что Nemerle обладает мощнейшей функцией вывода типов.
Фактически тип переменной expr является PExpr. Это можно указать явно:
def expr : Nemerle.Compiler.Parsetree.PExpr = <[
  when (a == 1)
      a = 2; ]>;

Примечание: Естественно, что как и в C# указывать полный путь к типу не обязательно. Nemerle.Compiler.Parsetree можно было задать в using-е.

Теперь вы достаточно знаете чтобы понять суть макроса из первого сообщения этой темы. Напомню его код:
using System.Console;

macro TestMacro()
{
  WriteLine("compile-time");
  <[ WriteLine("run-time") ]>;
}

Что же мы видим в этом макросе?
А видим мы два вызова метода WriteLine(). Один просто внутри тела макроса, а второй внутри «кавычек».
Так как макрос вызывается во время компиляции, то первый вызов WriteLine():
WriteLine("compile-time");

выведет строку "compile-time" в окно вывода компилятора. Важно понят, что этот код, выполняемый во время компиляции. Я всего лишь вывел строчку в окно, но с тем же успехом я мог бы подсоединиться к БД и считать из нее метаинформацию. В общем, я волен делать в нем все что угодно.
Вторая строка кода не выполняется во время компиляции. Они заключена в «ковычки». Это приводит к тому, что компилятор преобразует ее в AST и его нам.
Так как Nemerle ориентирован на выражения, в нем не нужно писать «return», чтобы возвратить значение функции. Последнее выражение в последовательности автоматически становится возвращаемым значением функции (в данном случае макроса TestMacro()). Если бы в C# поддерживались макросы и квази-цитирование, то этот код записывался бы на C# примерно так:
macro RExpr TestMacro()
{
  WriteLine("compile-time");
  return <[ WriteLine("run-time") ]>;
}

думаю, вы уже без проблем должны проводить аналогии между C# и Nemerle-ом. Так что оставлю вам самим задачу угадать откуда взялся RExpr после ключевого слова macro .

Квази-цитирование (quasi-quotation)

Теперь настала пора понять, что же означает приставка «квази».
Изменим немного наш пример:
macro TestMacro(myName)
{
  WriteLine("Compile-time. myName = " + myName.ToString());
  <[ WriteLine("Run-time.\n Hallo, " + $myName) ]>;
}

За одно придется изменить и код применения макроса на следующий:
TestMacro("Vlad");
def a = "VladD2";
TestMacro(a);

Нажмем F5 находясь в файле содержащем последний код... Вот что мы получим при этом в окне вывода:
>build-and-run.cmd test-001
--# Compiling Macro-assembly #---
---------------------------------
--- Compiling target assembly ---
---------------------------------
Compile-time. myName = "Vlad"
Compile-time. myName = a
--------------- OK -----------------
--Run: test-001.exe
.
Run-time.
 Hallo, Vlad
Run-time.
 Hallo, VladD2
>Exit code: 0

Теперь разберемся с каждой строкой макроса по отедльности.
Первое что изменилось в макросе – это то, что мы добавили параметр «myName».
Опять же не думайте, что он не типизированный. Его тип Nemerle выведет из дальнейшего использования. Чуть позже мы вернемся к вопросу о типе параметра этого макроса а сейчас пока что разберем остальные строки.
В строке:
WriteLine("Compile-time. myName = " + myName.ToString());

Мы выводим в окно компилятора значение содержащееся в параметре myName преобразовывая его в строку.
Примечание: Все объекты Nemerle – это автоматически объекты .NET-а, так что не странно, что у них реализованы методы класса object.
Теперь давайте поглядим, что же выводят эти строки?
При вызове макроса следующим абазом:
TestMacro("Vlad");

указанная строчка выводит:
Compile-time. myName = "Vlad"

А при вызове его так:
def a = "VladD2";
TestMacro(a);

мы получаем:
Compile-time. myName = a

Почему же мы во втором случае не получили текстовое значение помещенное в переменную «a»? Дело в том, что myName – это не строковая переменная, а переменная содержащая AST-ветку описывающую передаваемое в макрос выражение. В первом случае нам был передан литерал, а во втором переменная. Именно по этому, мы видим то что видим.
Попробуем проверить мое предположение. Для этого добавим в макрос перед строчкой:
WriteLine("Compile-time. myName = " + myName.ToString());

еще одну стрчку:
WriteLine(myName.GetType());

она выведет реальный тип выражения. Выполним компиляцию и поглядим на результат:
---------------------------------
--- Compiling target assembly ---
---------------------------------
Nemerle.Compiler.Parsetree.PExpr+Literal
Compile-time. myName = "Vlad"
Nemerle.Compiler.Parsetree.PExpr+Ref
Compile-time. myName = a
...

Результат полностью подтверждает мои ожидания.
Остается разобраться, что же такое PExpr+Literal и PExpr+Ref.
Лезем в Рефлектор и видим, что это классы вложенные в класс PExpr являющиеся его наследниками. Таким образом мы можем сделать четкий вывод, что в макрос переданы AST-ветки описывающие выражения Nemerle. Причем в первом случае это строковый литерал, а во втором – ссылка на переменную.
Теперь перейдем к строке макроса:
  <[ WriteLine("Run-time.\n Hallo, " + $myName) ]>;

Эта строка и является конечной целью повествования этого рздела.
Она тоже изменилась. Как и в предыдущей строке в ней я попытался прибавить к константной строке строку, содержащуюся в параметре.
Но в данном случае присутствуют два важных отличия.
1. Я не вызываю метод ToString().
2. Перед именем параметра макроса стоит символ «$».
Возникает резонный вопрос, а почему собсвенно?
Дело в том, что для предыдущих строк myName являлся переменной. А для цитируемого кода myName переменной являться не будет. Если я напишу:
  <[ WriteLine("Run-time.\n Hallo, " + myName.ToString()) ]>;

то компиляция макроса пройдет «на ура», но при его применении я получу сообщения об ошибке:
...
test-001.n:4:1:4:10: error: unbound name `myName.ToString'
Nemerle.Compiler.Parsetree.PExpr+Ref
Compile-time. myName = a
test-001.n:6:1:6:10: error: unbound name `myName.ToString'
...

Причем, заметьте! Код макроса не смотря на ошибки выполняется. А сообщения об ошибках я получаю уже от компилятора компилирующего сгенерированный макросом код.
Так происходит потому, что области видимости имен макросов и области видимости кода из которых эти макросы вызываются не пересекаются. Макросы Nemerle-a являются так называемыми гигиеническими. Использовать имена из вызывающего кода можно, но для этого придется постараться. Это уберегает от ошибок связанных с перекрытием имен. Так что даже если мы в взывающем коде напишем:
def myName = "xxx";
TestMacro("Vlad");

то ничего не изменится и мы получим все то же сообщение:
test-001.n:5:1:5:10: error: unbound name `myName.ToString'

Что же делать? Как получить доступ к внешним именам?
Ответ – никак! Точенее этого не нужно делать.
Мы получили в качестве параметра выражение. И мы можем внедрить его внутрь возвращаемого макросом выражения.
В принципе, произвести такое внедрение можно написав код просматривающий формируемое AST и модифицирующий его. Но это довольно сложно. Чтобы упростить подобные операции и было придумано квази-цитирование!
Внутри цитируемого кода мы можем вставлять, скажем так, активный контент. То есть нечто, что будет вычисляться перед возвратом из макроса.
Именно этой возможностью я и воспользовался чтобы внедрить ссылку на параметр макроса внутрь генерируемого кода. Символ «$» перед именем «myName» в строке:
<[ WriteLine("Run-time.\n Hallo, " + $myName) ]>;

Как раз и указывает компилятору Nemerle-а, что имя myName нужно рассматривать как этот самый активный кнтент.
Получается, что это уже не просто цитирование. Вот по этому его и назвали квази-цитированием.

Наверно вам интересно, что же в итоге попадает в код исполняемого модуля? Мне тоже это интересно (хотя я и догадываюсь – что). По этому я декомпилировал полученный исполняемый файл. Вот что я увидил:
Console.WriteLine("Run-time.\n Hallo, Vlad");
string text1 = "VladD2";
Console.WriteLine("Run-time.\n Hallo, " + text1);

Обратите внимание, что в первом случае получилась константная строка, а во втором код конкатинации переменной со строкой. Несомненно первый случай является результатом оптимизаций компилятора Nemerle-a.
Не трудно догадаться, что если в качестве параметра макроса передать выражение, то компилятор подставит его вместо параметра.
А что будет если тип выражения окажется несовместимым со строкой?
Проведем смелый научный эксперимент и передадим макросу в качестве параметра выражение «1 + 2»:
TestMacro(1 + 2);

Компилятор отреагировал довольно ожидаемым образом:
test-001.n:5:1:5:10: error: each overload has an error during call:
test-001.n:5:1:5:10: error:   overload #1, method System.String.op_Addition(left : string, right : string) : string
test-001.n:5:1:5:10: error: in argument #2 (right), needed a string, got int: System.Int32 is not a subtype of System.String [simple require]
...

С нашими знаниями мы без труда определим, что макрос просто хочет строку в качестве параметра. Можно сказать, что вывод типов в Nemerle-е опять «рулит», но откровенно говоря за такую «рулежку» можно и в бубен схлопотать если нашим макросом воспользуется кто-то довольно здоровый и невыдержанный (как я) .
Что же делать?
Выхода есть два. И оба они хорошие. Самый простой четко указать в месте применения, что мы хотим иметь дело со строкой. Для этого обсуждаемую строку макроса нужно переписать следующим образом:
<[ WriteLine("Run-time.\n Hallo, " + ($myName : string)) ]>;

Если после этого скомпилировать код, то мы получим совершенно вменяемое сообщение об ошибке:
test-001.n:5:1:5:10: error: expected string, got int in type-enforced expression: System.Int32 is not a subtype of System.String [simple require]

В принципе, этого достаточно в большинстве случаев, но душа как всегда хочет большего. Можно ли попытаться добиться этого большего?
А как же? Мы же обладаем всей мощью компиляторостроителей! Просто изменим код следующим образом:
  <[ WriteLine("Run-time.\n Hallo, " + System.Convert.ToString($myName)) ]>;

и вуаля...
Теперь наш макрос стал значительно более гибким. Компилируем:
TestMacro(1 + 2);
TestMacro(1 + 2098098);
TestMacro("Vlad");
def a = "VladD2";
TestMacro(a);

и получаем:
>build-and-run.cmd test-001
--# Compiling Macro-assembly #---
---------------------------------
--- Compiling target assembly ---
---------------------------------
Nemerle.Compiler.Parsetree.PExpr+Call
Compile-time. myName = 1 + 2
Nemerle.Compiler.Parsetree.PExpr+Call
Compile-time. myName = 1 + 2098098
Nemerle.Compiler.Parsetree.PExpr+Literal
Compile-time. myName = "Vlad"
Nemerle.Compiler.Parsetree.PExpr+Ref
Compile-time. myName = a
--------------- OK -----------------
--Run: test-001.exe
.
Run-time.
 Hallo, 3
Run-time.
 Hallo, 2098099
Run-time.
 Hallo, Vlad
Run-time.
 Hallo, VladD2
>Exit code: 0

А что же у нес теперь «под копотом»? Сейчас декомпильнем :
Console.WriteLine("Run-time.\n Hallo, " + Convert.ToString((sbyte) 3));
Console.WriteLine("Run-time.\n Hallo, " + Convert.ToString(0x2003b3));
Console.WriteLine("Run-time.\n Hallo, " + Convert.ToString("Vlad"));
string text1 = "VladD2";
Console.WriteLine("Run-time.\n Hallo, " + Convert.ToString(text1));

А что если скормить нечто, что Convert-ору не по зубам:
TestMacro(System.Console);

Все в порядке! Мы получаем довольно разумное сообщение:
test-001.n:5:11:5:25: error: none of the meanings of `System.Console' meets the type ?:

И это мы еще не использовали таких возможностей макросов как обращение к информации о типах выражений и анализу AST!

В общем, даже на таком простом примере видно насколько мощной вещью являются макросы Nemerle.

Продолжение следует.
... << RSDN@Home 1.2.0 alpha rev. 637>>
http://nemerle.org/Banners/?g=dark
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re: Изучаем макросы Nemerle
От: VladGalkin Украина  
Дата: 19.02.06 18:55
Оценка: :)
Здравствуйте, VladD2, Вы писали:

Влад, помогите пожалуйста в священной борьбе в ЖЖ!
... << RSDN@Home 1.1.4 stable rev. 510>>
ДЭ!
Re[2]: Изучаем макросы Nemerle
От: WolfHound  
Дата: 19.02.06 19:36
Оценка:
Здравствуйте, VladGalkin, Вы писали:

VG>Влад, помогите пожалуйста в священной борьбе в ЖЖ!

ЖЖ в сад! Нам тут священнгой войны хватает.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[3]: Изучаем макросы Nemerle
От: VladGalkin Украина  
Дата: 19.02.06 19:47
Оценка:
Здравствуйте, WolfHound, Вы писали:

WH>ЖЖ в сад! Нам тут священнгой войны хватает.

Не смею спорить с господином Модератором, предложение было скорее шуточное, чем серьезное.
... << RSDN@Home 1.1.4 stable rev. 510>>
ДЭ!
Re[2]: Изучаем макросы Nemerle
От: VladD2 Российская Империя www.nemerle.org
Дата: 20.02.06 16:20
Оценка:
Здравствуйте, VladGalkin, Вы писали:

VG>Влад, помогите пожалуйста в священной борьбе в ЖЖ!


Зимы мы уже дождались. Так что зазывай всех врагов (оппонентов) сюда. И будем их мочить в с... ээ... на РСДН.
... << RSDN@Home 1.2.0 alpha rev. 637>>
http://nemerle.org/Banners/?g=dark
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: Изучаем макросы Nemerle
От: VladGalkin Украина  
Дата: 20.02.06 17:34
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Зимы мы уже дождались. Так что зазывай всех врагов (оппонентов) сюда. И будем их мочить в с... ээ... на РСДН.


"Самое главное не спугнуть. Будем брать по одному" Зазываю, линки даю, не идут.
... << RSDN@Home 1.1.4 stable rev. 510>>
ДЭ!
Re[4]: Изучаем макросы Nemerle
От: VladD2 Российская Империя www.nemerle.org
Дата: 20.02.06 18:35
Оценка:
Здравствуйте, VladGalkin, Вы писали:

VG>"Самое главное не спугнуть. Будем брать по одному" Зазываю, линки даю, не идут.


Значит боятся. Ведь так проще жить.
... << RSDN@Home 1.2.0 alpha rev. 637>>
http://nemerle.org/Banners/?g=dark
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[5]: Изучаем макросы Nemerle
От: Vermicious Knid  
Дата: 20.02.06 20:40
Оценка:
VG>>"Самое главное не спугнуть. Будем брать по одному" Зазываю, линки даю, не идут.
VD>Значит боятся. Ведь так проще жить.

Кое кто из них уже здесь был и успел "отличиться". Я уверен, что некий товарищ mauhuur это никто иной как забаненный(?) WinniePoh.

Такую манеру общения ни с чем не спутаешь, цитирую:

> Еще-бы все они писаны на старом добром С.
Нет, ламеришко.
....
....
Так что, глупое вы ламерьё, идите читать http://www.paulgraham.com/

И не позорьтесь, и так вы слишком уж сильно на ничтожество похожи.


Вообще хорошо, что не идут. ЖЖ-шной манеры общения здесь только и не хватало.
Re[2]: Изучаем макросы Nemerle
От: CrazyPit  
Дата: 20.02.06 20:47
Оценка: +1 :)
Здравствуйте, VladGalkin, Вы писали:

VG>Здравствуйте, VladD2, Вы писали:


VG>Влад, помогите пожалуйста в священной борьбе в ЖЖ! :)


Спасибо за ссылку! Весёлый топик — Маухур, как обычно, зажигает коллектив:))
Re[6]: Изучаем макросы Nemerle
От: CrazyPit  
Дата: 20.02.06 20:51
Оценка:
Здравствуйте, Vermicious Knid, Вы писали:

VG>>>"Самое главное не спугнуть. Будем брать по одному" :)) Зазываю, линки даю, не идут. :xz:

VD>>Значит боятся. Ведь так проще жить.

VK>Кое кто из них уже здесь был и успел "отличиться". :))) Я уверен, что некий товарищ mauhuur это никто иной как забаненный(?) WinniePoh.


Похож конечно, но он в одном топики поставил Гвидо на ряду с Кнутом и Грэмом, что от Маухура слышать весьма странно.

VK>Такую манеру общения ни с чем не спутаешь, цитирую:

VK>

>> Еще-бы все они писаны на старом добром С.
VK>Нет, ламеришко.
VK>....
VK>....
VK>Так что, глупое вы ламерьё, идите читать http://www.paulgraham.com/

VK>И не позорьтесь, и так вы слишком уж сильно на ничтожество похожи.


Хотя может и он.

VK>Вообще хорошо, что не идут. ЖЖ-шной манеры общения здесь только и не хватало. :-\
Re[6]: Изучаем макросы Nemerle
От: WolfHound  
Дата: 20.02.06 22:54
Оценка: :))
Здравствуйте, Vermicious Knid, Вы писали:

VK>Вообще хорошо, что не идут. ЖЖ-шной манеры общения здесь только и не хватало.

Не волнуйся... на RSDN баня большая... на всех хватит...
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[6]: Изучаем макросы Nemerle
От: Cyberax Марс  
Дата: 21.02.06 07:17
Оценка: :)
Vermicious Knid wrote:
> Вообще хорошо, что не идут. ЖЖ-шной манеры общения здесь только и не
> хватало.
Это не ЖЖ, это известный FIDOшник — Виталий Луговской.
Posted via RSDN NNTP Server 2.0
Sapienti sat!
Re[7]: Изучаем макросы Nemerle
От: Dog  
Дата: 21.02.06 17:50
Оценка:
>> Вообще хорошо, что не идут. ЖЖ-шной манеры общения здесь только и не
>> хватало.
C>Это не ЖЖ, это известный FIDOшник — Виталий Луговской.
это диагноз
... << RSDN@Home 1.2.0 alpha rev. 631>>
http://rsdn.org/File/27746/bel.gif
Re[6]: Изучаем макросы Nemerle
От: vvotan Россия  
Дата: 22.02.06 09:41
Оценка:
Здравствуйте, Vermicious Knid, Вы писали:

VK>Такую манеру общения ни с чем не спутаешь, цитирую:

VK>

>> Еще-бы все они писаны на старом добром С.
VK>Нет, ламеришко.
VK>....
VK>....
VK>Так что, глупое вы ламерьё, идите читать http://www.paulgraham.com/

VK>И не позорьтесь, и так вы слишком уж сильно на ничтожество похожи.


Луговский?
--
Sergey Chadov

... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re: Микро-аддин для VS 2005
От: Oyster Украина https://github.com/devoyster
Дата: 06.03.06 18:32
Оценка: 95 (11) +1
Здравствуйте, VladD2, Вы писали:

Я всё время пользовался исключительно SciTE для работы с Nemerle, но для серьёзных проектов он как-то слабо подходит. Мне как минимум не хватает solutions/проектов, не хватает дебага и, наконец, не хватает VS 2005 IDE Я, конечно, надеюсь, что плагин для VS когда-нибудь доделают, но ждать как-то неохота.

Сегодня я прочитал вот это вот сообщение — Re[5]: Снова о Nemerle или профанация не пройдет :)
Автор: xhalt
Дата: 06.03.06
— и сделал парочку project/item templates для VS 2005. Шаблоны вполне стандартные:

Их можно установить, распаковав файлик Nemerle-VS2005-MicroAddin.zip и скопировав папочку "Templates" прямо в "My Documents\Visual Studio 2005". После этого в студии появятся проекты с префиксом "Nemerle" (во вкладке "Visual C#" под "My Templates" — это в окошке создания проекта) и project items с таким же префиксом (при добавлении нового айтема).

Для того, чтобы студия не ругалась на проекты (мол, targets не те) и для Build Action="Compile" по умолчанию для файлов с расширением .n надо ещё запустить файлик "NemerleImport.reg" из того же архива.

Самый приятный результат всех этих действий — наличие проектов и возможность дебага. Самый огромный недостаток — полное отсутствие подсветки синтаксиса (впрочем, какую-никакую подсветку можно организовать, связав расширение .n с одним из стандартных редакторов, как писал xtile
Автор: xhalt
Дата: 06.03.06
) и какого бы ни было Intellisense.

Надеюсь, будет полезно.
http://rsdn.org/File/27948/bf.gif
Re: Изучаем макросы Nemerle
От: xhalt Украина  
Дата: 07.03.06 11:40
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Единственный способ развеить скепсис — это попробовать.

+1

Мне вот (как и многим другим) понравилась э... "микроядерная архитектура"
компилятора Nemerle..

Интересно, но что помешало авторам Memerle,
реализовать ключевое слово "macro" не как часть компилятора а тоже макросом?

либо на самом себе же себе:
macro @macro( ... )
syntax ( "macro", ... )
...


либо, если сложности с self-hosting'ом, напрямую:
public class Macro : IMacro
{
  public Run (...) : PExpr  { /* здесь уже имеющимися средствами генерируем AST */}
  public SyntaxExpression (...) : ... { /* здесь описываем синтаксис*/}
    //... и т.п.
}


Или это излишнее усложнение?
... << RSDN@Home 1.2.0 alpha rev. 0>>


Предлагаю работу в Киеве
Автор:
Дата: 04.05.06
Re[2]: Изучаем макросы Nemerle
От: VladD2 Российская Империя www.nemerle.org
Дата: 07.03.06 15:04
Оценка:
Здравствуйте, xhalt, Вы писали:

X>Интересно, но что помешало авторам Memerle,

X>реализовать ключевое слово "macro" не как часть компилятора а тоже макросом?

А ты погляди исходники компилятора. Там почти все так и есть.
... << RSDN@Home 1.2.0 alpha rev. 637>>
http://nemerle.org/Banners/?g=dark
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: Изучаем макросы Nemerle
От: xhalt Украина  
Дата: 07.03.06 15:44
Оценка:
Здравствуйте, VladD2, Вы писали:
X>>реализовать ключевое слово "macro" не как часть компилятора а тоже макросом?
VD>А ты погляди исходники компилятора. Там почти все так и есть.
Дык смотрел уже. Реализация в "основном ядре". К слову, достаточно компактная и легко читаемая.
Показалось что можно ещё упростить... Впрочем, возможно только лишь показалось
... << RSDN@Home 1.2.0 alpha rev. 0>>


Предлагаю работу в Киеве
Автор:
Дата: 04.05.06
Re[4]: Изучаем макросы Nemerle
От: VladD2 Российская Империя www.nemerle.org
Дата: 07.03.06 18:01
Оценка:
Здравствуйте, xhalt, Вы писали:

X>Дык смотрел уже. Реализация в "основном ядре".


Ну, мало ли где. По сути сделано так же.

X>К слову, достаточно компактная и легко читаемая.


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

X>Показалось что можно ещё упростить... Впрочем, возможно только лишь показалось


Совершенство не достижимо, но стремиться к нему стоит.
... << RSDN@Home 1.2.0 alpha rev. 637>>
http://nemerle.org/Banners/?g=dark
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.