RFC on range design for D2
Steven Schveighoffer
schveiguy at yahoo.com
Wed Sep 10 16:17:48 PDT 2008
"Sergey Gromov" wrote
> You don't mention here which iterator usage pattern you are trying to
> model with ranges. I can think of at least two.
>
> 1. You use a single bidirectional 'center' iterator, center == 5. As
> one would naturally do with iterators. Note then that whenever you use
> your center for, say, backward iteration, you reconstruct the actual
> range by calling list.begin. You do it on each iteration. No wonder it
> stays valid even if you remove the first element in the meantime: you're
> constructing your range from scratch anyway. If you want to model this
> pattern with ranges---no problem, keep an empty 'center' range, center
> == (5,5), and reconstruct backward iteration range,
>
> reverse = all.before(center);
>
> whenever you need to iterate, then
>
> center = reverse.end;
>
> This 'center' range, being slightly less efficient, stays valid and
> becomes invalid in exactly the same conditions as your classical
> iterator.
This is exactly the pattern I use. I agree that your example would solve
the problem, I hadn't thought of an empty range to be a cursor, that is
clever!
The only missing piece to your solution is that I must construct the range
after the center range in order to access the value to see where I need to
go.
What I see as the biggest downside is the cumbersome and verbose code of
moving the 'iterator' around, as every time I want to move forward, I
construct a new range, and every time I want to move backwards I construct a
new range (and construct a new 'center' afterwards). So a 'move back one'
looks like:
auto before = all.before(center);
if(!before.isEmpty)
center = before.pop.end;
And to move forward it's:
auto after = all.after(center);
if(!after.isEmpty)
center = after.next.begin;
To get the value there, I have to do:
all.after(center).left // or whatever gets decided as the 'get first value
of range' member
or if opStar is used:
*all.after(center);
I much prefer:
forward:
if(center != list.end)
++center;
reverse:
if(center != list.begin)
--center;
get value:
*center;
Especially without all the extra overhead
I see both methods as being just as open to mistakes, the first more-so, and
more difficult to comprehend (at least for me).
-Steve
More information about the Digitalmars-d-announce
mailing list