Re[2]: Лучший синтаксис для перебора значений
От: igna Россия  
Дата: 06.04.06 08:10
Оценка: 43 (3) +2
foreach (i in 0 .. 3) // 0, 1, 2, 3

foreach (i in 0 ..< 3) // 0, 1, 2

foreach (i in 0 <.. 3) // 1, 2, 3

foreach (i in 0 <..< 3) // 1, 2
Re[7]: Лучший синтаксис для перебора значений
От: Oyster Украина https://github.com/devoyster
Дата: 06.04.06 08:23
Оценка: 15 (1)
Здравствуйте, Кодёнок, Вы писали:

Кё>Кстати, а как в Nemerle сослаться на оператор + для класса, например, для целых? Пробовал System.Int32.op_Add и System.Int32.operator+, в документации не знаю где искать.


Всё проще
Автор: Vermicious Knid
Дата: 25.03.06
:

list.FoldLeft(0, _ + _) / x.Length
Re[2]: Лучший синтаксис для перебора значений
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 06.04.06 08:24
Оценка: 7 (1)
Здравствуйте, Lazy Cjow Rhrr, Вы писали:

LCR>Хм. Будет немного непривычно:

LCR>
LCR>12.times { say 'hello' }          // _1 принимает значения от 0 до 11
LCR>(2..16).times { say 'hello '_1 }  // _1 принимает значения от 2 до 16
LCR>(10+.5).times { say 'hello '_1 }  // _1 принимает значения от 5 до 14 (то есть 10 различных значений)
LCR>


irb(main):013:0> 5.times { |i| puts "- #{i} -" }
- 0 -
- 1 -
- 2 -
- 3 -
- 4 -
=> 5
irb(main):014:0> (2..4).each { |i| puts "= #{i} =" }
= 2 =
= 3 =
= 4 =
=> 2..4
irb(main):015:0> (2...4).each { |i| puts "= #{i} =" }
= 2 =
= 3 =
=> 2...4
irb(main):016:0>


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re: Лучший синтаксис для перебора значений
От: AndrewVK Россия http://blogs.rsdn.org/avk
Дата: 06.04.06 08:42
Оценка:
Здравствуйте, VladD2, Вы писали:

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


foreach, но так, чтобы сначала указывалась коллекция, а затем элемент. Т.е. как нибудь так (жирным выделены ключевые слова):
string[] strs = new {"a", "b", "c"};
on (strs each string str)
    Console.WriteLine(str);

Опционально можно так:
string[] strs = new {"a", "b", "c"};
on (strs each string str with index)
    Console.WriteLine(strs[index]);

Что же касается интервалов, степов и т.п., то тут я согласен с Синклером, для этого достаточно иметь набор соотв. итераторов.
... << RSDN@Home 1.2.0 alpha rev. 642>>
AVK Blog
Re: Лучший синтаксис для перебора значений
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 06.04.06 08:45
Оценка: 8 (1) +1
Здравствуйте, VladD2, Вы писали:

VD>В Руби для таких случаев используется синтаксис:

VD>
VD>foreach (i in 0...3) // то есть добавляется третья точка.
VD>

VD>Но это не интуитивно и легко путается с вариантом с двумя точками.

Это ты где в Ruby цикл foreach нашел?
В Ruby есть понятие Range, которое записывается либо с двумя точками (тогда это соответствует [a,b]), либо с тремя точками (что соответствует [a,b)).

Кроме того, если нужно перебрать все элементы контейнера, то используются методы each:
[1, 2, 3, 4].each { |item| ... }

Если нужно выполнить определенное количество циклов, то используется метод times:
10.times { |n| ... }

Если нужно перебрать значения от a до b, то можно использовать методы upto, downto или Range#each:
1.upto(10) { ... } # от 1 до 10.
10.downto(1) { ... } # от 10 до 1.
(1..10).each { ... } # от 1 до 10.
(1...10).each { ... } # от 1 до 9


Цикла foreach в Ruby нет. Есть for in, для которого важно, чтобы в итерируемом объекте был метод each:

Вы можете использовать for для итерации по любому объекту, который отвечает на метод each, например Array или Range:

for i in ['fee', 'fi', 'fo', 'fum']
  print i, " "
end
for i in 1..3
  print i, " "
end
for i in File.open("ordinal").find_all { |l| l =~ /d$/}
  print i.chomp, " "
end

выводит:
fee fi fo fum 1 2 3 second third


Как только ваш класс определяет соответствующий метод each, вы можете использовать цикл for для его обхода
class Periods
  def each
    yield "Classical"
    yield "Jazz"
    yield "Rock"
  end
end

periods = Periods.new
for genre in periods
  print genre, " "
end

выводит:
Classical Jazz Rock

Programming Ruby, глава Expressions


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re[3]: Лучший синтаксис для перебора значений
От: adontz Грузия http://adontz.wordpress.com/
Дата: 06.04.06 09:14
Оценка: 9 (1) +1
Здравствуйте, igna, Вы писали:

I>
I>foreach (i in 0 .. 3) // 0, 1, 2, 3
I>

I>
I>foreach (i in 0 ..< 3) // 0, 1, 2
I>

I>
I>foreach (i in 0 <.. 3) // 1, 2, 3
I>

I>
I>foreach (i in 0 <..< 3) // 1, 2
I>


Тогда уже

foreach (0 = i = 3) // 0, 1, 2, 3

foreach (0 = i < 3) // 0, 1, 2

foreach (0 < i = 3) // 1, 2, 3

foreach (0 < i < 3) // 1, 2

что кажется уже предлагали
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[3]: Лучший синтаксис для перебора значений
От: kan_izh Великобритания  
Дата: 06.04.06 09:19
Оценка:
VladD2 wrote:

> _>Честно говоря, С++ синтаксис мне больше всего нравится, т.к. более

> гибок, позволяет перебирать не только целые числа в некоем интервале с
> шагом 1, но фактически что угодно и как угодно.
>
> Понимаш ли в чем дело? С-шный for никто не отменяет. Но его гибкость
> выливается в ошибки и усложнение чтения кода когда он используется для
> простых вещей.
>
> Мы (люди) думаем абстракциями. Когда ты пишешь:
>
> for (int i = 0; i < array.Length; i++)
> array[i] = f(array[i]);
>
>
> ты реально думашь не так:
> 1. Объявить перменную целого типа.
> 2. Инициализировать ее нулем который является нижней границей массива.
> 3. Выполнять условие цикла пока переменная не превысит значения длинны
> массива.
> 4. На каждой итерации увеличить индекс на один.
> 5. Вынуть значение по индексу находящемуся в ячейке с номером заданным в
> переменной i.
> 6. Применить к значению функцию f().
> 7. Поместить значение преобразования по индексу находящемуся в ячейке с
> номером заданным в переменной i.

Нет, конечно. Просто рассматривается цикл как конструкция из 3 частей — начальное условие; условие окончания; операция
получения следующего элемента.
И не важно, что перебирается — индексы, родители, или диапозон, или ещё что...
Мне нравится единообразие при многообразии
for(int i=0; i<arguments.length; i+=2)
{
    map[arguments[i]] = arguments[i+1];
}
for(Node *parent = theNode; parent; parent = parent->getParent())
{
}
for(Range r(collection); r; ++r)
{
  cout << *r;
}
char *list[] = {"aaa", "bbb", "ccc", NULL};
for(char **elem = list; *elem; ++elem)
{
}

//Синтаксис типа этого будет совершенно не в тему. А преимущества какие?
foreach( int i=[0..arguments.length) )
{
   cout << arguments[i];
}
// Ещё можно оправдать такой синтаксис, тем, что выкидывается неиспользуемое здесь понятие "индекс"/"итератор", 
используется только "коллекция" и её "элемент коллекции".
foreach int arg(arguments)
{
   cout << arg;
}

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

Резюме. В перле приняли правильное решение — перебор элементов массива (без итераторов) foreach и универсальный сишный for.
Posted via RSDN NNTP Server 2.0
но это не зря, хотя, может быть, невзначай
гÅрмония мира не знает границ — сейчас мы будем пить чай
Re: Лучший синтаксис для перебора значений
От: last_hardcoder  
Дата: 06.04.06 09:38
Оценка:
Здравствуйте, VladD2, Вы писали:

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


VD>Например, в С/С++ для этого используется императивный стиль:

VD>
VD>for (int i = 0; i < len; i++)
VD>

VD>но этот синтаксис слишком громоздок и может приводить к случайным ошибкам (так как императивен).

VD>Во многих ЯП можно увидить синтаксис вроде:

VD>
VD>foreach (i in 0..3) // выдает последовательность 0, 1, 2, 3
VD>

VD>этот синтаксис хорош, но неудобен когда нужно перебрать значения индекса некой коллекции:
VD>
VD>foreach (i in 0..array.Length - 1) // не нравится этот "- 1"
VD>


Мне кажется, тут должно быть два паттерна: паттерн диапазона и паттерн перебора. Перебор применим как к диапазонам, так и к контейнерам. А диапазон можно использовать отдельно от перебора. Например создать контейнер, содержащий диапазоны.
Re[4]: Лучший синтаксис для перебора значений
От: igna Россия  
Дата: 06.04.06 09:41
Оценка:
Здравствуйте, adontz, Вы писали:

A>Тогда уже


A>foreach (0 = i < 3) // 0, 1, 2


Имелось ввиду так?:

foreach (0 <= i < 3) // 0, 1, 2


Согласен, foreach (0 <= i < 3) выглядит естественнее чем foreach (i in 0 ..< 3), но во-первых я предложил, как с минимальными изменениями снять конкретные нарекания вызванные конкретной конструкцией, а во-вторых кто-то возможно найдет, что

foreach (i in offset + delta * (m..n))

более понятен нежели

foreach (offset + delta * m <= i <= offset + delta * n)
Re[2]: Лучший синтаксис для перебора значений
От: Кодт Россия  
Дата: 06.04.06 09:41
Оценка: 1 (1) +1
> Почему бы не использовать традиционную математическую нотацию для inclusive/exclusive:

Используйте полуинтервалы [x1..x2) и будет щасте.
Это и С++ные указатели/итераторы за концом массива, и питоньи диапазоны.

#! python

for x in range(   3) : print x  # 0 1 2
for x in range(3, 7) : print x  #       3 4 5 6
for x in range(7,10) : print x  #               7 8 9
Posted via RSDN NNTP Server 2.0
Перекуём баги на фичи!
Re: Лучший синтаксис для перебора значений
От: z00n  
Дата: 06.04.06 10:31
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>
VD>foreach (i in 0..array.Length - 1) // не нравится этот "- 1"
VD>


-- Haskell

-- так:
take array.Length [0..]
-- или так:
[i | i <- [0..], i < array.Length]


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

Как в Python,Haskell etc. — совокупность генераторов и гардов, другими словами: List comprehension.
Re[2]: Лучший синтаксис для перебора значений
От: Andrei N.Sobchuck Украина www.smalltalk.ru
Дата: 06.04.06 10:55
Оценка: 8 (1)
Здравствуйте, last_hardcoder, Вы писали:

_>Мне кажется, тут должно быть два паттерна: паттерн диапазона и паттерн перебора. Перебор применим как к диапазонам, так и к контейнерам. А диапазон можно использовать отдельно от перебора. Например создать контейнер, содержащий диапазоны.


Кстати. Вот в St есть #do: (типа foreach) и select: (фильрация коллекции). Наблюдательные программисты подметили, что иногда встречается патерн
типа (коллекция select: [ ...условие... ]) do: [ ...действие...]. То есть выбираем подмножество и его обрабатываем. Результат появление внутреннего итератора с фильтром типа коллекция select: [ ...условие... ] do: [ ...действие...]. От предідущего єтот вариант отличается не только отсутсвием кругліх скобок, но и отсутсвием промежуточной временной коллекции.

Что касается диапазона вообще (класс Interval в ST), то я видел, что бы он применялся только на низком уровне, при реализации самих методов do:, select: и пр.

Что касается исходного примера:

foreach (i in 0..array.Length - 1) // не нравится этот "- 1"


то в ST являются нормальным явлением методы коллекций first, last, allButFirst, allButLast, copyWithouFirst, copyWithouLast. Названия, вроде, говорят сами за себя.
http://www.smalltalk.ru | << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Я ненавижу Hibernate
Автор: Andrei N.Sobchuck
Дата: 08.01.08
!
Re[2]: Лучший синтаксис для перебора значений
От: VladD2 Российская Империя www.nemerle.org
Дата: 06.04.06 11:48
Оценка: :)
Здравствуйте, Sinclair, Вы писали:

S>Мысль такая:

...

S>Предполагается набор перегруженных конструкторов для указания step. Предполагается наличие свойства Reverse для обращения обхода. Предполагается наличие операций пересечения/объединения интервалов. Велком


Сысль зравая и я даже дошел до ее аналога. Только уже в новом формате. Можно написать простенокий макрос который будет определять тип коллекции и формировать включающий дипазон (ее я озвучил здесь).
macro IndexesOf(collection) 
{ 
   // In real code one needs to do check type of collection and make specialized code 
   <[ $$[0..collection.Length - 1] ]> 
}
...
foreach (i in IndexesOf(myArray)) 
  ...


Более того товарищь Москаль сказал, что в Немерле в ближайшее время появятся расширяющие методы и расширяющие макросы. Это позволит писать так:
foreach (i in myarr.Indexes)
  ...


Причем реально код будет переписываться в тот самый for.

Так что ваша улыбочка, сэр, в конце сообщения ниуместна!
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[7]: Лучший синтаксис для перебора значений
От: VladD2 Российская Империя www.nemerle.org
Дата: 06.04.06 11:48
Оценка: +1
Здравствуйте, Кодёнок, Вы писали:

Кё>Совершенно верно, питон Но можно и другие языки:

Кё>
Кё>return Nemerle.Collections.List.FoldLeft(lisT, 0, fun(a,b) {a+b}) / x.Length
Кё>


Можно проще:
lisT.FoldLeft(0, _ + _) . lisT.Length
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[3]: Лучший синтаксис для перебора значений
От: Lazy Cjow Rhrr Россия lj://_lcr_
Дата: 06.04.06 11:53
Оценка:
eao197,

E>5.times { |i| puts "- #{i} -" }


Здорово! Я теперь понял, откуда у меня такие фантазии
quicksort =: (($:@(<#[),(=#[),$:@(>#[)) ({~ ?@#)) ^: (1<#)
Re[2]: Лучший синтаксис для перебора значений
От: VladD2 Российская Империя www.nemerle.org
Дата: 06.04.06 11:56
Оценка:
Здравствуйте, eao197, Вы писали:

E>Это ты где в Ruby цикл foreach нашел?


В Руби есть задание диапазонов с тремя точками (0...3). Об этом и шала речь.
Тебе же снова хочется обсудить вопрос не имеющий отношения к делу.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[2]: Лучший синтаксис для перебора значений
От: VladD2 Российская Империя www.nemerle.org
Дата: 06.04.06 11:56
Оценка:
Здравствуйте, z00n, Вы писали:

Z>Как в Python,Haskell etc. — совокупность генераторов и гардов, другими словами: List comprehension.


List comprehension перебор для такого случая. В общем-то диапазон и является простым случаем List comprehension, но все же городить нагромождения по этому поводу наверно не стоит.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[4]: Лучший синтаксис для перебора значений
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 06.04.06 12:02
Оценка:
Здравствуйте, Lazy Cjow Rhrr, Вы писали:

LCR>
E>>5.times { |i| puts "- #{i} -" }
LCR>


LCR>Здорово! Я теперь понял, откуда у меня такие фантазии


Так ведь, с кем поведешься...

Кстати, если само значение счетчика не интересует, то можно писать просто:
5.times { puts "---" }


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re[5]: Лучший синтаксис для перебора значений
От: Andrei N.Sobchuck Украина www.smalltalk.ru
Дата: 06.04.06 12:14
Оценка:
Здравствуйте, eao197, Вы писали:

E>>>5.times { |i| puts "- #{i} -" }


E>Кстати, если само значение счетчика не интересует, то можно писать просто:

E>
E>5.times { puts "---" }
E>


Прикольно. Во-первых, в ST этот метод никогда не передаёт значение счетчика и для того, что бы его получить приходится писать 1 to: 5 do: [...]. Не то чтобы я этим часто пользовался, но когда изредка пишу какие-то тестики, то постоянно об этом забываю. Во-вторых, только сейчас заметил, что название метода в ST слегка неконсистентно — timesRepeat:. Почему Repeat если можно было сделать просто times:, или timesDo: на крайняк. История, блин.
http://www.smalltalk.ru | << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Я ненавижу Hibernate
Автор: Andrei N.Sobchuck
Дата: 08.01.08
!
Re[3]: Лучший синтаксис для перебора значений
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 06.04.06 12:30
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>В Руби есть задание диапазонов с тремя точками (0...3). Об этом и шала речь.

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

Я хотел сказать, что в Ruby нет оператора foreach.
А так же то, что приведенная тобой для Ruby запись:
foreach (i in 0...3)

не соответствует примеру для других языков:
foreach (i in 0..3) // выдает последовательность 0, 1, 2, 3

Поскольку для Ruby будет выдана последовательность 0, 1, 2 (без тройки). Т.е. твои два примера не эквивалентны.
Если же ты хочешь именно 0,1,2,3, то следует писать диапазон именно с двумя точками.

Так что я не пытаюсь увести разговор в сторону. а исправляю фактические ошибки. Относись к ним как опечаткам, которые заметил читатель.


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