[Nemerle] Расширения библиотеки макросов
От: Алексей П Россия  
Дата: 21.10.06 11:25
Оценка:
Предлагаю внести в "стандартную" библиотеку макросов Nemerle циклы forinc и fordec, грамотная реализация есть. Давно сделал это для себя, действительно удобно. Вот forinc:

macro @forinc (loop, body)
    syntax("forinc", "(", loop, ")", body)
{
    def (var, start, condition) = match(loop)
    {
        | <[ $(var : name) = $start .. $end ]> => (var, start, <[ $(var : name) <= $end ]>)
                    
        | <[ $(var : name) <= $_ ]> 
        | <[ $(var : name) < $_ ]> => (var, <[ 0 ]>, loop)
                    
        | e => Message.FatalError ($"the syntax is 'forinc(x = start .. end)' or 'forinc(x {< | <=} end)', got $e")
    }
    def loop = Nemerle.Macros.Symbol (Util.tmpname ("forinc_"));

    <[ 
        def $(loop : name) ($(var : name) : int) 
        { 
            match($(var : name))
            {
                | _ when $condition =>
                    $(Name.Global ("_N_break") : name) : {
                        $(Name.Global ("_N_continue") : name) : {
                            $body; 
                        }
                        $(loop : name) ($(var : name) + 1) 
                    }
                | _ => ()
            }
        }; 
        $(loop : name) ($start) 
    ]>
}


fordec по аналогии, могу выдать.
Синтаксис такой:
forinc(iter = start .. end) // как в паскале
forinc(iter <= end) // [0, end]
forinc(iter < end) // [0, end)
Итератор неизменяемый, код генерится более оптимальный чем для while или for (за счет match c guard-ом вместо when, это тоже можнно бы подправить в when).
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>

30.01.07 18:08: Перенесено модератором из 'Декларативное программирование' — IT
Re: [Nemerle] Расширения библиотеки макросов
От: Андрей Хропов Россия  
Дата: 21.10.06 12:20
Оценка:
Здравствуйте, Алексей П, Вы писали:

АП>Предлагаю внести в "стандартную" библиотеку макросов Nemerle циклы forinc и fordec, грамотная реализация есть. Давно сделал это для себя, действительно удобно. Вот forinc:


АП>fordec по аналогии, могу выдать.

АП>Синтаксис такой:
АП>forinc(iter = start .. end) // как в паскале
АП>forinc(iter <= end) // [0, end]
АП>forinc(iter < end) // [0, end)
АП>Итератор неизменяемый, код генерится более оптимальный чем для while или for (за счет match c guard-ом вместо when, это тоже можнно бы подправить в when).

Ну это скорее к авторам, лучше пиши сюда или сюда.
А вообще зачем слишком много ключевых слов?
можно уже сейчас писать
foreach(iter in $[start..end])

или
foreach(_ in $[start..end])

если не нужно значение iter.
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re[2]: [Nemerle] Расширения библиотеки макросов
От: Алексей П Россия  
Дата: 21.10.06 12:29
Оценка:
Здравствуйте, Андрей Хропов, Вы писали:

АХ>Ну это скорее к авторам, лучше пиши сюда или сюда.

Ну лучше сначала тут обсудим...

АХ>
АХ>foreach(iter in $[start..end])
АХ>

Неудобно — много букв

АХ>или

АХ>
АХ>foreach(_ in $[start..end])
АХ>

АХ>если не нужно значение iter.
А для этого есть repeat.

Идея в том, что специальный синтаксис для часто (ну не очень, но всё-таки) нужных форм должен быть простым для написания и прочтения. forinc(i < data.Length) значительно красивее чем foreach(i in $[0..data.Length — 1]), разве нет?
А по поводу ключевых слов — так их в Немерле и так больше чем в других языках.
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re[3]: [Nemerle] Расширения библиотеки макросов
От: RustM Россия  
Дата: 21.10.06 19:14
Оценка:
Здравствуйте, Алексей П, Вы писали:

АП>Здравствуйте, Андрей Хропов, Вы писали:


АХ>>
АХ>>foreach(iter in $[start..end])
АХ>>

АП>Неудобно — много букв

Что та, что эта конструкция в современных средствах ака IDE на набор конструкции не уйдет более двух-трех нажатии, так что отмазка не канает

АП>Идея в том, что специальный синтаксис для часто (ну не очень, но всё-таки) нужных форм должен быть простым для написания и прочтения. forinc(i < data.Length) значительно красивее чем foreach(i in $[0..data.Length — 1]), разве нет?


АП>А по поводу ключевых слов — так их в Немерле и так больше чем в других языках.


Не пойдет. А если у меня например часто возникает ситуция с шагом более единицы, что будем добавлять еще и forincstep и fordecstep Не слишком ли будет:
// с количеством ключевых слов (макросов) мог напутать, но идея думаю понятна
for
foreach
while
do while
repeat
// плюс 
forinc
fordec
forincstep
fordecstep

... << RSDN@Home 1.2.0 alpha rev. 655>>
Re: [Nemerle] Расширения библиотеки макросов
От: VladD2 Российская Империя www.nemerle.org
Дата: 21.10.06 23:28
Оценка:
Здравствуйте, Алексей П, Вы писали:

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

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

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

Если же вдруг требуется перебор с индексом, то у стандартных коллекций есть метод IterI. Например, вот как он выглядит для массива:
public IterI [T] (this arr : array [T], f : int * T -> void) : void

а вот как применяется:
using System.Console;
using Nemerle.Utility;

def ary = array[10,20,30,40,50,60];
ary.IterI((index, value) => 
    WriteLine(if (index % 2 == 0) $"Odd:  $value" else $"Even: $value"));

Этот код выведет:
Odd:  10
Even: 20
Odd:  30
Even: 40
Odd:  50
Even: 60

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

Но по жизни куда удобнее пользоваться разными Map и т.п.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[2]: [Nemerle] Расширения библиотеки макросов
От: Алексей П Россия  
Дата: 22.10.06 07:11
Оценка:
Здравствуйте, VladD2, Вы писали:

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

Я не с шарпа, я с дельфей

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

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

VD>Но по жизни куда удобнее пользоваться разными Map и т.п.

Всё это мне конечно известно, действительно в функциональном стиле я пишу гораздо чаще чем обычные циклы... видимо, forinc так и останется только у меня.
А вот подправить код, генерирумый на макрос when и соответственно на match(что-то : bool) совсем не помешает — смотрел reflector-ом, вместо
if(a >= b) break;

(это с гардом) генерится
if((a < b) ? 1 : 0 != 1) break;
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re[3]: [Nemerle] Расширения библиотеки макросов
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.10.06 15:31
Оценка:
Здравствуйте, Алексей П, Вы писали:

АП>Я не с шарпа, я с дельфей


Это ничего не меняет. Даже наоборот. Дельфи еще более императивный язык.

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

АП>Да, кроме того, что создается замыкание вместо простых условных переходов. Иногда удобно, а иногда и не нужно.

И какая тебе разница? Выглядит как утка, плавает как утка, летает как утка, крякает как утка... значит утка.

АП>А вот подправить код, генерирумый на макрос when и соответственно на match(что-то : bool) совсем не помешает — смотрел reflector-ом, вместо

АП>
АП>if(a >= b) break;
АП>

АП>(это с гардом) генерится
АП>
АП>if((a < b) ? 1 : 0 != 1) break;
АП>


Это мелкие недочеты генератора кода. Они ни на что кроме микроскопического увеличения исполняемого файла не влияют, так как устраняются JIT-ом.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.