June 01, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Mehrdad Attachments:
| On Fri, Jun 1, 2012 at 7:40 PM, Mehrdad <wfunction@hotmail.com> wrote:
> Another way to phrase it would be that D is forcing you to to use templates where they really aren't meant to be used. :\
>
>
No. I am working on a Domain Specific Language and want to cut on the code the end user has to write. If I were working on an application I would have coded differently and I am sure D provides for various other ways.
So D is not forcing me here to use this syntax :-)
Regards
- Puneet
| |||
June 01, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Steven Schveighoffer Attachments:
| Thanks Steve
With your help I am able to make it work.
Thanks and Regards
- Puneet
void callfoo(alias F, T) (T t) {
void delegate() dg;
dg.funcptr = &F;
dg.ptr = cast(void *)t;
dg();
}
class Foo {
void foo() {
import std.stdio;
writeln("This Works");
}
}
void main() {
Foo f = new Foo();
callfoo!(Foo.foo)(f);
}
| |||
June 01, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Jacob Carlborg | On Fri, 01 Jun 2012 10:14:26 -0400, Jacob Carlborg <doob@me.com> wrote:
> On 2012-06-01 15:51, Steven Schveighoffer wrote:
>> On Fri, 01 Jun 2012 09:25:57 -0400, d coder <dlang.coder@gmail.com> wrote:
>>> Class Bar(alias F) {
>>> // Call F in some function here
>>> }
>>>
>>> Class Foo {
>>> void foo();
>>> Bar!(() {foo();}) bar;
>>> }
>>>
>>> Again this does not work. Maybe I am expecting too much from D. :-) I am
>>> somewhat aware of the issues involved here. I have seen some earlier D
>>> threads.
>>
>> lambdas cannot exist outside a function scope. This is a limitation of D
>> that has been pointed out before, and I think it should be made
>> available, but don't hold your breath :) D is just starting to get more
>> filled out in the area of lambdas.
>
> That can't work since there is no this-reference for "foo"?
I'm surprised at some things that work with alias. It sometimes seems like black magic.
Consider that this does work:
void incx(alias x)()
{
x++;
}
void main()
{
int x = 0;
incx!x();
assert(x == 1);
}
now, consider that when incx!x is compiled, the stack frame for main doesn't exist! So how does the compiler build it?
I suppose the issue with the lambda in class scope issue above is different, because incx has an implicit reference back to its caller's frame through the stack pointer.
But it seems like there may be a way that it could work. For example, create an implicit, final (private) member function which has the body of the lambda. Then construct the Bar type with an alias to that function. Would it need a stack frame to work? I have no idea :) Again, black magic.
-Steve
| |||
June 01, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Steven Schveighoffer Attachments:
| Steve One small thing. As you said I might declare a delegate in an alternate fashion that is by saying "void delegate() dg;". But would it be possible to rewrite the following declaration in a way that avoids naming foo explicitly. I would just have an alias for foo. I am asking this to cover the cases where foo might have a list of arguments and I want to create a delegate with the same list of arguments. typeof(&F.init.foo) dg; Regards - Puneet | |||
June 01, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to d coder | On Fri, 01 Jun 2012 10:33:07 -0400, d coder <dlang.coder@gmail.com> wrote:
> Steve
>
> One small thing. As you said I might declare a delegate in an alternate
> fashion that is by saying "void delegate() dg;".
>
> But would it be possible to rewrite the following declaration in a way that
> avoids naming foo explicitly. I would just have an alias for foo. I am
> asking this to cover the cases where foo might have a list of arguments and
> I want to create a delegate with the same list of arguments.
>
> typeof(&F.init.foo) dg;
It's possible. I'm not well versed enough in the traits templates of phobos to be able to tell you.
Start looking in std.traits and std.typecons.
There might even be something there that is exactly what you are looking for :)
-Steve
| |||
June 01, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Steven Schveighoffer | On 2012-06-01 16:30, Steven Schveighoffer wrote: > I'm surprised at some things that work with alias. It sometimes seems > like black magic. > > Consider that this does work: > > void incx(alias x)() > { > x++; > } > > void main() > { > int x = 0; > incx!x(); > assert(x == 1); > } > > > now, consider that when incx!x is compiled, the stack frame for main > doesn't exist! So how does the compiler build it? > > I suppose the issue with the lambda in class scope issue above is > different, because incx has an implicit reference back to its caller's > frame through the stack pointer. > > But it seems like there may be a way that it could work. For example, > create an implicit, final (private) member function which has the body > of the lambda. Then construct the Bar type with an alias to that > function. Would it need a stack frame to work? I have no idea :) Again, > black magic. > > -Steve I don't see this example as strange. I mean, the same would work with a pointer or ref. The lambda on the other hand was create in a scope where the this-reference wasn't available. But I don't know, as you say, black magic. -- /Jacob Carlborg | |||
June 01, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Jacob Carlborg | On Fri, 01 Jun 2012 10:57:34 -0400, Jacob Carlborg <doob@me.com> wrote:
> I don't see this example as strange. I mean, the same would work with a pointer or ref.
An alias is not a pointer or ref, and it's not passed in at runtime, it's passed in at compile time.
-Steve
| |||
June 02, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to d coder | On Friday, 1 June 2012 at 14:33:59 UTC, d coder wrote:
> Steve
>
> One small thing. As you said I might declare a delegate in an alternate
> fashion that is by saying "void delegate() dg;".
>
> But would it be possible to rewrite the following declaration in a way that
> avoids naming foo explicitly. I would just have an alias for foo. I am
> asking this to cover the cases where foo might have a list of arguments and
> I want to create a delegate with the same list of arguments.
>
> typeof(&F.init.foo) dg;
>
>
> Regards
> - Puneet
The language/standard library do not provide a straightforward
way of constructing a delegate type from a corresponding function
(of function pointer) type, so you will have to go hacky. It is
easiest to use std.functional.toDelegate (don't ask why it is in
std.functional):
import std.functional : toDelegate;
auto ref call(alias fn, T, A...)(T t, auto ref A args)
{
typeof(toDelegate(&fn)) dg;
dg.ptr = cast(void*)t;
dg.funcptr = &fn;
return dg(args);
}
At the moment, the ref-ness of the return type is not determined
correctly because of a compiler bug. Otherwise, that works mostly
fine.
Note, that the delegate approach comes with performance penalty,
which dmd cannot currently optimize out. So it is slower than a
direct call.
In a parallel reality D would have a separate kind of (pointers
to) functions that take a context pointer. Something like
extern(DWithContext) function(...)
Then such functions/function pointers could be made callable
directly with the context pointer as the first argument. Also, a
delegate's funcptr would be typed correctly.
| |||
June 02, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Max Samukha | On Saturday, 2 June 2012 at 17:33:04 UTC, Max Samukha wrote:
> (of function pointer) type, so you will have to go hacky. It is
> easiest to use std.functional.toDelegate (don't ask why it is in
> std.functional):
s/of function pointer/or function pointer/
| |||
June 02, 2012 Re: Calling an alias for a Class method in another scope | ||||
|---|---|---|---|---|
| ||||
Posted in reply to Max Samukha Attachments:
| >
>
> At the moment, the ref-ness of the return type is not determined correctly because of a compiler bug. Otherwise, that works mostly fine.
>
>
Thank you Max for showing me toDelegate. But I find that it does not work even for function arguments with default values. So for the moment I will trod the path Steve showed me.
Regards
- Puneet
| |||
Copyright © 1999-2021 by the D Language Foundation
Permalink
Reply