Выйти из двух циклов сразу.
От: WolfHound  
Дата: 26.05.06 13:57
Оценка:
Развлекался я тут с макросами...
    class LoopHelper
    {
        static ExitName : string = "_N_exit_";
        public static MakeExitName(name : object) : string
        {
        | null => ExitName
        | _    => ExitName + name.ToString()
        }
    }

    macro MBreak (loopName)
    syntax ("exit", Optional(loopName))
    {
        <[ $(PT.Name.Global (LoopHelper.MakeExitName(loopName)) : name) () ]>
    }
  
    macro @loop (body, cond, loopName)
    syntax ("loop", Optional("[", loopName, "]"), "(", cond, ")", body) 
    {
        def loop = Nemerle.Macros.Symbol (Util.tmpname ("loop_"));

        <[ 
            $(PT.Name.Global (LoopHelper.MakeExitName(loopName)) : name) :     
            {
                def $(loop : name) () : void 
                {
                    when($cond)
                    {
                        $body;
                        $(loop : name) ();
                    }
                } 
                $(loop : name) (); 
            }
        ]>
    }

и использование
        loop [my_super_puper_loop] (false)
        {
            loop  (false)
            {
                when(false)
                    exit ;
                when(false)
                    exit my_super_puper_loop;
            }
        }

И вот мне подумалось, а не добавить ли эту функциональность к стандартным for, foreach, while и к их break и continue?
Написанный код это не сломает.
Кто как думает?

ЗЫ Может уже пора форум по Немерле создать?
... << RSDN@Home 1.1.4 beta 6a rev. 436>>

26.05.06 18:48: Перенесено модератором из 'Интеграция Nemerle и Visual Studio' — VladD2
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re: Выйти из двух циклов сразу.
От: VladD2 Российская Империя www.nemerle.org
Дата: 26.05.06 15:45
Оценка:
Здравствуйте, WolfHound, Вы писали:

...

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

WH>И вот мне подумалось, а не добавить ли эту функциональность к стандартным for, foreach, while и к их break и continue?


Думаю не стоит. Уже есть блоки кода.

WH>ЗЫ Может уже пора форум по Немерле создать?


Незнаю. Пока что трафик не большой.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[2]: Выйти из двух циклов сразу.
От: WolfHound  
Дата: 26.05.06 16:15
Оценка:
Здравствуйте, VladD2, Вы писали:

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

В макросах нету.

VD>Думаю не стоит. Уже есть блоки кода.

Я в курсе. Как ты думаешь через что работают break, continue, return?
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re: Выйти из двух циклов сразу.
От: VladD2 Российская Империя www.nemerle.org
Дата: 26.05.06 16:18
Оценка:
Здравствуйте, WolfHound, Вы писали:

Собственно пример применения блоков кода:
using System.Console;

def value = myBlock: // Объявление блока кода
{
  foreach (i in [1 .. 10])
    foreach (x in [i .. i * i])
      when (x > 30)
        myBlock(x); // принудительный выход из блока кода.
  0;
}

WriteLine(value);
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: Выйти из двух циклов сразу.
От: VladD2 Российская Империя www.nemerle.org
Дата: 26.05.06 16:20
Оценка:
Здравствуйте, WolfHound, Вы писали:

WH>В макросах нету.


Чего в макросах нету?

VD>>Думаю не стоит. Уже есть блоки кода.

WH>Я в курсе. Как ты думаешь через что работают break, continue, return?

Ну, а зачем тогда нужны спец-велосипеды? Проблема выхода из двух и более циклов возникает так редко, что блоки кода решают все проблемы в лучшем виде.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re: Выйти из двух циклов сразу.
От: WolfHound  
Дата: 27.05.06 12:07
Оценка:
Здравствуйте, WolfHound, Вы писали:

Еще чего я не понимаю это почему они так странно обошлись с if'ом. Ведь можно же было сделать нормальный.
    macro @if_ (cond, then, else_)
    syntax ("if_", "(", cond, ")", then, Optional("else_", else_))
    {
        def thenValue = then;
        def elseValue = match(else_)
        {
        | null => <[()]>
        | _    => else_
        }

        <[ 
            match($cond)
            {
            | true => $thenValue
            | false => $elseValue
            }
        ]>
    }

        if_(1==1)
            if_(2==3)
                WriteLine(2);
            else_
                WriteLine(3);

        def s = if_(false)
            "asd";
        else_
            "qwe";
        WriteLine(s);
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[2]: Выйти из двух циклов сразу.
От: VladD2 Российская Империя www.nemerle.org
Дата: 27.05.06 13:46
Оценка:
Здравствуйте, WolfHound, Вы писали:

WH>Еще чего я не понимаю это почему они так странно обошлись с if'ом. Ведь можно же было сделать нормальный.


Устранили классическую неоднозначность. Сосбвтенно об этом где-то на сайте языка было сказано.

Учитывая, что if за одно заменяет и оператор "? :" заменяет, это выглядит довольно разумно. Ведь выражение может быть в одну строку и отступами показать что происходит не выйдет.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: Выйти из двух циклов сразу.
От: WolfHound  
Дата: 27.05.06 14:15
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Устранили классическую неоднозначность. Сосбвтенно об этом где-то на сайте языка было сказано.

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

VD>Учитывая, что if за одно заменяет и оператор "? :" заменяет, это выглядит довольно разумно. Ведь выражение может быть в одну строку и отступами показать что происходит не выйдет.

И в чем проблема? Мой вариант тоже может заменить ? :. Причем точно также как и их.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[4]: Выйти из двух циклов сразу.
От: VladD2 Российская Империя www.nemerle.org
Дата: 27.05.06 16:18
Оценка:
Здравствуйте, WolfHound, Вы писали:

WH>Вот только както плохо они ее устранили. Вот в обероне ее действительно устранили, а тут всеравно нужно както отступами все выделять.


Полностью устратили. Неоднозначностии нет. А отступы это уже для читабельности. Без инх и в Обероне будет зе зашибись.

WH>Короче не вижу смысла.


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

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

WH>И в чем проблема? Мой вариант тоже может заменить ? :. Причем точно также как и их.


Проблема во многократно вложенных if/else-ах. В общем, поройся по их сайту. Там было весьма доходчивое объяснение.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re: Выйти из двух циклов сразу.
От: little_alex  
Дата: 28.05.06 10:35
Оценка:
Здравствуйте, WolfHound, Вы писали:


WH>
WH> .......
WH>        def loop = Nemerle.Macros.Symbol (Util.tmpname ("loop_"));
WH> .........
WH>


А зачем это ? Макросы то все равно гигиенические.
Наверное и так должно работать (проверить не могу )
   macro @loop (body, cond, loopName)
    syntax ("loop", Optional("[", loopName, "]"), "(", cond, ")", body) 
    {
        <[ 
            $(PT.Name.Global (LoopHelper.MakeExitName(loopName)) : name) :     
            {
                def my_loop () : void 
                {
                    when($cond)
                    {
                        $body;
                        my_loop ();
                    }
                } 
                my_loop (); 
            }
        ]>
    }
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.