www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - for ranges

reply Russel Winder via Digitalmars-d-learn <digitalmars-d-learn puremagic.com> writes:
Playing with factorial implementations, as you do. I had a D
implementation using ulong. Not sensible obviously since overflow is a
bit of a problem. But the code worked, as did the tests. Now converting
to BigInt and=E2=80=A6

The standard explicit iteration form uses a loop:

	for(i; 2..n+1)

for n =3D 0 or 1 this loop doesn't loop since the range is [,). However
for BigInt:

	for(i; two..n + one)

the loop starts at 0 and just keeps on going. This is clearly not good.

Am I having a mental breakdown or is this a real bug?


--=20
Russel.
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D
Dr Russel Winder      t: +44 20 7585 2200   voip: sip:russel.winder ekiga.n=
et
41 Buckmaster Road    m: +44 7770 465 077   xmpp: russel winder.org.uk
London SW11 1EN, UK   w: www.russel.org.uk  skype: russel_winder
Jan 22 2015
next sibling parent reply "bearophile" <bearophileHUGS lycos.com> writes:
Russel Winder:

 However for BigInt:

 	for(i; two..n + one)

 the loop starts at 0 and just keeps on going. This is clearly 
 not good.
It works for me: void main() { import std.stdio, std.bigint; immutable BigInt one = 1; immutable BigInt two = 2; uint n = 100; foreach (immutable i; two .. n + one) i.writeln; } Bye, bearophile
Jan 22 2015
parent reply "bearophile" <bearophileHUGS lycos.com> writes:
 It works for me:
Sorry, you are right, it loops: void main() { import std.stdio, std.bigint; immutable BigInt one = 1; immutable BigInt two = 2; uint n = 0; foreach (immutable i; two .. n + one) i.writeln; } Bye, bearophile
Jan 22 2015
parent Russel Winder via Digitalmars-d-learn <digitalmars-d-learn puremagic.com> writes:
On Thu, 2015-01-22 at 16:48 +0000, bearophile via Digitalmars-d-learn
wrote:
 It works for me:
=20 Sorry, you are right, it loops:
So it is a bug, and I now have to find out how to report it! --=20 Russel. =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D Dr Russel Winder t: +44 20 7585 2200 voip: sip:russel.winder ekiga.n= et 41 Buckmaster Road m: +44 7770 465 077 xmpp: russel winder.org.uk London SW11 1EN, UK w: www.russel.org.uk skype: russel_winder
Jan 22 2015
prev sibling next sibling parent Steven Schveighoffer <schveiguy yahoo.com> writes:
On 1/22/15 11:41 AM, Russel Winder via Digitalmars-d-learn wrote:
 Playing with factorial implementations, as you do. I had a D
 implementation using ulong. Not sensible obviously since overflow is a
 bit of a problem. But the code worked, as did the tests. Now converting
 to BigInt and…

 The standard explicit iteration form uses a loop:

 	for(i; 2..n+1)

 for n = 0 or 1 this loop doesn't loop since the range is [,). However
 for BigInt:

 	for(i; two..n + one)

 the loop starts at 0 and just keeps on going. This is clearly not good.

 Am I having a mental breakdown or is this a real bug?
The issue: import std.stdio; struct S { int x; int opCmp(const S other) const { writeln("compare"); return x < other.x ? -1 : x > other.x ? 1 : 0;} bool opEquals(const S other) const { writeln("equals"); return x == other.x;} ref S opOpAssign(string op)(int other) { mixin("x " ~ op ~ "= other;"); return this; } } void main() { immutable S one = S(1); immutable S two = S(2); foreach(s; one..two) {} } output: equals equals So foreach(S; one..two) translates to: for(S x = one; x != two; x += 1) which explains the infinite loop. I'm almost positive foreach(x; 1..2) uses comparison instead of equality to check for end condition. -Steve
Jan 22 2015
prev sibling parent reply "ixid" <adamsibson hotmail.com> writes:
On Thursday, 22 January 2015 at 16:41:49 UTC, Russel Winder wrote:
 Playing with factorial implementations, as you do. I had a D
 implementation using ulong. Not sensible obviously since 
 overflow is a
 bit of a problem. But the code worked, as did the tests. Now 
 converting
 to BigInt and…

 The standard explicit iteration form uses a loop:

 	for(i; 2..n+1)

 for n = 0 or 1 this loop doesn't loop since the range is [,). 
 However
 for BigInt:

 	for(i; two..n + one)

 the loop starts at 0 and just keeps on going. This is clearly 
 not good.

 Am I having a mental breakdown or is this a real bug?
In general it feels as if BigInt needs more work as it doesn't work with simple generic code in too many cases. Templates get confused by invocation with a literal and a BigInt for example when it should have a single type. Literals feel too strongly typed or too weakly implicitly convertible.
Jan 23 2015
parent Steven Schveighoffer <schveiguy yahoo.com> writes:
On 1/23/15 4:44 AM, ixid wrote:
 On Thursday, 22 January 2015 at 16:41:49 UTC, Russel Winder wrote:
 Playing with factorial implementations, as you do. I had a D
 implementation using ulong. Not sensible obviously since overflow is a
 bit of a problem. But the code worked, as did the tests. Now converting
 to BigInt and…

 The standard explicit iteration form uses a loop:

     for(i; 2..n+1)

 for n = 0 or 1 this loop doesn't loop since the range is [,). However
 for BigInt:

     for(i; two..n + one)

 the loop starts at 0 and just keeps on going. This is clearly not good.

 Am I having a mental breakdown or is this a real bug?
In general it feels as if BigInt needs more work as it doesn't work with simple generic code in too many cases. Templates get confused by invocation with a literal and a BigInt for example when it should have a single type. Literals feel too strongly typed or too weakly implicitly convertible.
This is not a BigInt problem, it's an inconsistency with foreach range. See my earlier post. -Steve
Jan 23 2015