On 5/12/22 12:51, ag0aep6g wrote:

>> auto iota(B, E, S)(B begin, E end, S step)
> [...]
>> {
>>     static struct Result
>>     {
>>         B current;
> [...]
>>         void popFront()
>>         {
> [...]
>>             current += step;
>>         }
>>     }
> [...]
>> }
>
> Mark iota's `begin` parameter as const. Then you don't need the cast,
> because `B` will be mutable.

Cool trick! Like this:

auto iota(B, E, S)(const(B) begin, E end, S step)
{
  // ...
}

It works with non-const values as well. So apparently it makes the function parameter const(B) and deduces B to be the non-const version of that, which always produces the non-const version.

And I've been thinking 'iota' may not be as suitable as I thought at first. I like the following even more:

  auto r0 = st
            .by(Duration(2))
            .take(5);

  auto r1 = st
            .by(Duration(2))
            .until(en);

A family of 'by' ovenloads can be defined or it can be templatized to be used as 'by!Duration(2)' etc.:

auto by(DateTime dt, Duration dur) {
  struct Result {
    DateTime front;
    Duration dur;

    enum empty = false;
    void popFront() { front += dur; }
  }

  return Result(dt, dur);
}

Just works. But one may want to provide an accessor for front().

Ali

Reply via email to