Plan for InputRange?
Dukc
ajieskola at gmail.com
Tue Sep 28 15:07:59 UTC 2021
Yesterday, I came across [this
bug](https://issues.dlang.org/show_bug.cgi?id=19544) that is
caused by design of std.range.interfaces. The problem is that
`InputRange` has an abstract member function `moveFront()`.
Why is this a problem, you could ask - if I'm able to get a
`front` of a range by copy, surely I can get it when I don't even
require a copy? This is all good and true with most types. But
`moveFront()` from `std.range.primitives`, just like
`core.lifetime.move`, will require the element to be a LValue.
`moveFront()` is smart enough to use copy with RValues if there
are no copy constructors or postblits, but with them a reference
access to `front` is required. It follows that the dynamic range
interfaces will not work at for ranges with RValue elements with
copy constructors:
```D
import std;
struct HasCC
{ inout this(ref inout typeof(this)){}
}
void main()
{ // will not compile
auto dynamicRange = repeat(HasCC.init).inputRangeObject;
}
```
What should we do about this? One could argue that `moveFront`
belongs to `InputAssignable` as opposed to `InputRange`, but I
think it would be too much breakage to change it like that
anymore.
Another option might be to say that `moveFront` should behave
just like `front` when `front` is a RValue. Either just in
`std.range.interfaces` or also in `std.range.primitives`. Perhaps
even `move` could behave like that? But maybe there is some
reason I'm missing why they do not act like that already?
We could also leave it just as is, documenting the limitation in
`std.range.interfaces`. It would not necessarily mean a permanent
defeat, because of possibility to fix it in Phobos V2 (Timeline
estimates on that, anyone?).
More information about the Digitalmars-d
mailing list