[Issue 5550] New: std.range.enumerate()
d-bugmail at puremagic.com
d-bugmail at puremagic.com
Tue Feb 8 17:04:03 PST 2011
http://d.puremagic.com/issues/show_bug.cgi?id=5550
Summary: std.range.enumerate()
Product: D
Version: D2
Platform: All
OS/Version: All
Status: NEW
Severity: enhancement
Priority: P2
Component: Phobos
AssignedTo: nobody at puremagic.com
ReportedBy: bearophile_hugs at eml.cc
--- Comment #0 from bearophile_hugs at eml.cc 2011-02-08 17:01:39 PST ---
I suggest to add an enumerate() to Phobos std.range module. An alternative name
is count().
enumerate() is a simple function, it takes one iterable and returns an iterable
of (index, item) pairs:
>>> list(enumerate("abcd"))
[(0, 'a'), (1, 'b'), (2, 'c'), (3, 'd')]
A second optional argument allows to define a start value different from zero:
>>> list(enumerate("abcd", 3))
[(3, 'a'), (4, 'b'), (5, 'c'), (6, 'd')]
This is an example usage of Python2.6 enumerate():
>>> comp = [1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1]
>>> [i for i,b in enumerate(comp) if not b]
[2, 3, 5, 7, 11, 13, 17, 19]
>>> comp = comp[2:]
>>> comp
[0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1]
>>> [i for i,b in enumerate(comp, 2) if not b]
[2, 3, 5, 7, 11, 13, 17, 19]
Here the input 'comp' is a list of bits (booleans) produced by a Sieve of
Eratosthenes, that represents the composite numbers. The desired output (a
sequence of primes) is a list of indexes where the value b is false, so it's
prime.
This is a D2 translation in procedural style:
import std.stdio;
void main() {
auto comp = [1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0,
1];
int[] result;
foreach (i, p; comp)
if (!p)
result ~= i;
writeln(result);
comp = comp[2..$];
result.length = 0;
foreach (i, p; comp)
if (!p)
result ~= i + 2;
writeln(result);
}
A translation in functional style:
import std.stdio, std.algorithm, std.range;
void main() {
auto comp = [1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0,
1];
auto result1 = map!q{a[0]}(filter!q{!a[1]}(zip(iota(comp.length), comp)));
writeln(result1);
comp = comp[2..$];
auto result2 = map!q{a[0]+2}(filter!q{!a[1]}(zip(iota(comp.length),
comp)));
writeln(result2);
}
An enumerate() allows to write simpler code:
import std.stdio, std.algorithm, std.range;
void main() {
auto comp = [1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0,
1];
auto result1 = map!q{a[0]}(filter!q{!a[1]}(enumerate(comp)));
writeln(result1);
comp = comp[2..$];
auto result2 = map!q{a[0]}(filter!q{!a[1]}(enumerate(comp, 2)));
writeln(result2);
}
zip(iota(foo.length), foo) becomes even worse when the iterable foo is lazy and
doesn't define a length:
zip(iota(walkLength(foo)), foo)
--
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
More information about the Digitalmars-d-bugs
mailing list