range simple toy problem

Xiaoxi xiaoxi at 163.com
Fri Jun 1 21:16:38 UTC 2018


On Friday, 1 June 2018 at 18:40:45 UTC, ag0aep6g wrote:
> On 06/01/2018 07:00 PM, Xiaoxi wrote:
>
> This prints "3 4 5 6 7 8 9":
>
> ----
> import std.range;
> import std.algorithm;
> import std.stdio;
>
> void main()
> {
>    auto s = "1 2 3 4 5 6 7 8 9";
>    auto iter = refRange(&s).splitter!(c => c == ' ').drop(2);
>    writeln(s); /* "3 4 5 6 7 8 9" */
> }
> ----
>
> Arguably, `.splitter(' ')` should work as well, but it doesn't.
>
> Warning: Large parts of Phobos, including `splitter`, have 
> problems handling a `RefRange`. So this might break down when 
> you take it beyond the toy stage.
> https://issues.dlang.org/show_bug.cgi?id=18657
>
>> split is just an example, it's a generic question if you chain 
>> multiple lazy functions and then consume a part of the data...
>
> Nitpick: `split` is not lazy. `splitter` is.
>
>> how do you know how to slice the original buffer to point to 
>> the unconsumed data?
>
> In my opinion, `refRange` should fit the bill here. But:
>
> 1) It's not always clear from the documentation how much a lazy 
> function actually pops. It might pop more than you expect, or 
> less.
> 2) As mentioned, `refRange` has compatibility issues with other 
> parts of Phobos.

Many thanks ye all for your helpful comments! Seems like 
std.range is a small minefield for beginners. std.algorithm is 
much easier and intuitive to use(my current code uses findSplit). 
However when std.range works, it really shines.

refRange is exactly what I needed, thanks! It is really worrisome 
that a function could pop too much or too little though, 
especially if it would change between D versions. Guess I need to 
add a good unit-test to handle that.



More information about the Digitalmars-d-learn mailing list