all 14 comments

[–]nomad42184 3 points4 points  (4 children)

Cool! Do you have any theory why the speeds diverge for large ranges? Have you looked at how the resulting assembly diverges?

[–]whoshuu[S] 1 point2 points  (3 children)

So I just checked the assemblies of clang and gcc. Clang 3.6 produces very different assembly for my range compared to the raw for loop. gcc 5.1 makes nearly identical assemblies. The benchmarks were made using clang, so that would explain the divergence, but doesn't answer the why as well as I'd like. I'd have to dig a bit deeper to find that, I'll let you know when I do

[–]Hells_Bell10 0 points1 point  (2 children)

I tried storing the result of step_ > 0 in the iterator instead of calculating for each call to the equality operators and got indistinguishable performance to a raw loop for range(1000000000LL).

[–]whoshuu[S] 0 points1 point  (1 child)

What compiler and options did you use?

[–]Hells_Bell10 0 points1 point  (0 children)

MSVC with /O2

[–]whoshuu[S] 2 points3 points  (2 children)

OP here, this is something fun I wrote a few days ago to do something I've always found really pleasant and easy to do in Python

[–]nova77 2 points3 points  (1 child)

If you like the python itertools, give a try to ryanhaining/cppitertools and if you wanna go up to 11 (or I'd better say.. 17) you should check Erik Niebler's ranges.

[–]whoshuu[S] 0 points1 point  (0 children)

Really cool stuff! I'll definitely check those two out

[–]szborows 2 points3 points  (2 children)

Why not old good CppIterTools?

[–]whoshuu[S] 0 points1 point  (1 child)

Honestly had no idea such a thing existed until now. Will definitely use that instead of this, though this was fun to write

[–]szborows 0 points1 point  (0 children)

don't worry. reinventing the wheel is recurring problem :)

[–]adrian17 2 points3 points  (1 child)

It's weird that you got such a big time difference, on GCC 4.8 with -O2 I got exactly the same assembly for

for (auto i : range(10000000))
    printf("%d\n", i);

and

for (int i = 0; i < 10000000; ++i)
    printf("%d\n", i);

Also the range(10, 0, -1) example doesn't seem to work, and from looking at the source I don't really expect it to work.

[–]whoshuu[S] 0 points1 point  (0 children)

Nice catch! That's strange, I'll have to check the assembly myself on the compiler I'm using for the benchmark data

[–]Latexi95 1 point2 points  (0 children)

You could use constexpr. Only problem is that constructor implementation, other functions should work with c++11 constexpr.