How to provide this arg or functor for algorithm?
anonymous via Digitalmars-d-learn
digitalmars-d-learn at puremagic.com
Mon Aug 17 05:38:03 PDT 2015
On Monday, 17 August 2015 at 10:28:33 UTC, thedeemon wrote:
> Nope, it "works" only because "r" is unreferenced and gets
> thrown out. Just try using r.front there, for example, and the
> error returns.
You're right, it falls short.
But I think r not being referenced is not exactly it. Using front
in Ali's func breaks it in the same way. And returning r from
func works.
Wait, returning r from func works? Yes:
----
auto func()(uint[] arr, uint context) @nogc
{
import std.algorithm;
auto r = arr[].map!(delegate(value) { return value * context;
});
return r;
}
void main() @nogc
{
uint[3] arr = [1,2,3];
uint context = 2;
auto r = func(arr[], context);
import std.algorithm: equal;
import std.range: only;
assert(equal(r, only(2, 4, 6)));
}
----
Is that supposed to compile? A closure is needed for the
delegate, isn't it? With @nogc, where is the closure stored? This
looks like an accepts-invalid bug to me.
It doesn't compile when func is not a template. So maybe the
check is broken for templates.
It also doesn't compile with 2.067, so this may be a regression.
Coming back to Ali's code, here's a version that shows that func
doesn't need template parameters, but it needs to be a template:
----
import std.stdio;
import std.algorithm;
struct Caller
{
uint method(uint value) pure @nogc {
return _context * value;
}
uint _context;
}
auto func()(uint[] arr, uint delegate(uint) pure @nogc d) @nogc
{
return arr.map!(d);
}
void main() @nogc
{
uint[3] arr = [1,2,3];
uint context = 2;
auto c = Caller(context);
auto d = &c.method;
auto r = func(arr[], d);
import std.algorithm: equal;
import std.range: only;
assert(equal(r, only(2, 4, 6)));
}
----
I think this relies on the same discrepancy as the problematic
code above.
More information about the Digitalmars-d-learn
mailing list