www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - alias this on module

reply Jonathan Marler <johnnymarler gmail.com> writes:
Any reason why "alias this" doesn't work at the module level?  If 
I recall correctly, a module is really just a "class" under the 
hood, but when I tried to use it I got:

Error: alias this can only be a member of aggregate, not module 
<module-name>
Apr 30 2017
next sibling parent reply Steven Schveighoffer <schveiguy yahoo.com> writes:
On 4/30/17 7:35 PM, Jonathan Marler wrote:
 Any reason why "alias this" doesn't work at the module level?  If I
 recall correctly, a module is really just a "class" under the hood, but
 when I tried to use it I got:

 Error: alias this can only be a member of aggregate, not module
 <module-name>
public import is to modules as alias this is to structs/classes :) -Steve
Apr 30 2017
parent reply Jonathan Marler <johnnymarler gmail.com> writes:
On Sunday, 30 April 2017 at 23:44:32 UTC, Steven Schveighoffer 
wrote:
 On 4/30/17 7:35 PM, Jonathan Marler wrote:
 Any reason why "alias this" doesn't work at the module level?  
 If I
 recall correctly, a module is really just a "class" under the 
 hood, but
 when I tried to use it I got:

 Error: alias this can only be a member of aggregate, not module
 <module-name>
public import is to modules as alias this is to structs/classes :) -Steve
They're actually different. // // File: mymodule.d // module mymodule; struct Foo { int bar; void baz(); } __gshared Foo foo; alias foo this; // using "alias this" on a module // // File: main.d // import mymodule; // now the symbol "x" refers to foo.x, and the symbol "baz" refers to foo.baz.
Apr 30 2017
parent reply Steven Schveighoffer <schveiguy yahoo.com> writes:
On 4/30/17 7:59 PM, Jonathan Marler wrote:
 On Sunday, 30 April 2017 at 23:44:32 UTC, Steven Schveighoffer wrote:
 On 4/30/17 7:35 PM, Jonathan Marler wrote:
 Any reason why "alias this" doesn't work at the module level?  If I
 recall correctly, a module is really just a "class" under the hood, but
 when I tried to use it I got:

 Error: alias this can only be a member of aggregate, not module
 <module-name>
public import is to modules as alias this is to structs/classes :)
They're actually different. // // File: mymodule.d // module mymodule; struct Foo { int bar; void baz(); } __gshared Foo foo; alias foo this; // using "alias this" on a module
So you want to alias a struct to a module? That's different than what I thought, I thought you wanted to alias one module's members into another. I can't see a reason why it couldn't be added as a feature. I admit I'm not seeing the benefit though. You could simulate this via a mixin. e.g.: void baz() { foo.baz; } property ref bar() { return foo.bar; } -Steve
May 01 2017
parent reply Jonathan Marler <johnnymarler gmail.com> writes:
On Monday, 1 May 2017 at 12:41:19 UTC, Steven Schveighoffer wrote:
 On 4/30/17 7:59 PM, Jonathan Marler wrote:
 On Sunday, 30 April 2017 at 23:44:32 UTC, Steven Schveighoffer 
 wrote:
 On 4/30/17 7:35 PM, Jonathan Marler wrote:
 Any reason why "alias this" doesn't work at the module 
 level?  If I
 recall correctly, a module is really just a "class" under 
 the hood, but
 when I tried to use it I got:

 Error: alias this can only be a member of aggregate, not 
 module
 <module-name>
public import is to modules as alias this is to structs/classes :)
They're actually different. // // File: mymodule.d // module mymodule; struct Foo { int bar; void baz(); } __gshared Foo foo; alias foo this; // using "alias this" on a module
So you want to alias a struct to a module? That's different than what I thought, I thought you wanted to alias one module's members into another. I can't see a reason why it couldn't be added as a feature. I admit I'm not seeing the benefit though. You could simulate this via a mixin. e.g.: void baz() { foo.baz; } property ref bar() { return foo.bar; } -Steve
Ya now you get it. It's not a big deal, it's just that after I thought about it, I couldn't think of a reason why it's not supported. I actually have an application for it too. Since modules are just classes under the hood, I was wondering if implementing it would be as simple as commenting out an error message like Andre's [nested import example](https://www.youtube.com/watch?v=3NihZVcZqto&t=183s&#t=27m15s)
May 01 2017
parent reply Petar Kirov [ZombineDev] <petar.p.kirov gmail.com> writes:
On Monday, 1 May 2017 at 21:50:02 UTC, Jonathan Marler wrote:
 On Monday, 1 May 2017 at 12:41:19 UTC, Steven Schveighoffer 
 wrote:
 On 4/30/17 7:59 PM, Jonathan Marler wrote:
 On Sunday, 30 April 2017 at 23:44:32 UTC, Steven 
 Schveighoffer wrote:
 On 4/30/17 7:35 PM, Jonathan Marler wrote:
 Any reason why "alias this" doesn't work at the module 
 level?  If I
 recall correctly, a module is really just a "class" under 
 the hood, but
 when I tried to use it I got:

 Error: alias this can only be a member of aggregate, not 
 module
 <module-name>
public import is to modules as alias this is to structs/classes :)
They're actually different. // // File: mymodule.d // module mymodule; struct Foo { int bar; void baz(); } __gshared Foo foo; alias foo this; // using "alias this" on a module
So you want to alias a struct to a module? That's different than what I thought, I thought you wanted to alias one module's members into another. I can't see a reason why it couldn't be added as a feature. I admit I'm not seeing the benefit though. You could simulate this via a mixin. e.g.: void baz() { foo.baz; } property ref bar() { return foo.bar; } -Steve
Ya now you get it. It's not a big deal, it's just that after I thought about it, I couldn't think of a reason why it's not supported. I actually have an application for it too. Since modules are just classes under the hood, I was wondering if implementing it would be as simple as commenting out an error message like Andre's [nested import example](https://www.youtube.com/watch?v=3NihZVcZqto&t=183s&#t=27m15s)
The common thing between modules and the other aggregate types (classes, interfaces, unions and structs) is that members of the former behave as if they were static members of the later. The difference, of course, is that since modules can have only static members, they can't be instantiated and by extension have no 'this' pointer/reference. Because of this I think 'alias member this' on the module level would be nonsensical. Keep in mind that 'alias member this' is a tool for establishing a subtyping relationship - i.e. 'this' instance can be used wherever 'member' can be used - and not just a way to do member access rewrite like opDispatch. There is no subtyping relationship between namespaces, which is what modules are effectively​. On the other hand, 'alias bar = foo.bar' and module level static opDispatch seem like perfectly reasonable and desirable features.
May 01 2017
parent Jonathan Marler <johnnymarler gmail.com> writes:
On Monday, 1 May 2017 at 23:06:00 UTC, Petar Kirov [ZombineDev] 
wrote:
 The common thing between modules and the other aggregate types 
 (classes, interfaces, unions and structs) is that members of 
 the former behave as if they were static members of the later. 
 The difference, of course, is that since modules can have only 
 static members, they can't be instantiated and by extension 
 have no 'this' pointer/reference. Because of this I think 
 'alias member this' on the module level would be nonsensical. 
 Keep in mind that 'alias member this' is a tool for 
 establishing a subtyping relationship - i.e. 'this' instance 
 can be used wherever 'member' can be used - and not just a way 
 to do member access rewrite like opDispatch. There is no 
 subtyping relationship between namespaces, which is what 
 modules are effectively​.

 On the other hand, 'alias bar = foo.bar' and module level 
 static opDispatch seem like perfectly reasonable and desirable 
 features.
It's true that "this" normally refers to an instance of a type, but that's not the case with "alias this". It's actually referring to the type itself, not an instance, so you can access static members through it. I've written an example that compiles and works to demonstrate this: import std.stdio; struct Foo { int x; } struct fakemodule { // a member of the fake module // Note that it has to be "static" to be analagous to a real module static Foo foo; // an "alias this" on the module (this isn't supported on a real module) alias foo this; } void main() { fakemodule.x = 3; // references fakemodule.foo.x // Print x using alias this and direct access writeln(fakemodule.x); writeln(fakemodule.foo.x); // Verify these expressions represent the same thing assert(&fakemodule.x == &fakemodule.foo.x); }
May 01 2017
prev sibling parent reply Meta <jared771 gmail.com> writes:
On Sunday, 30 April 2017 at 23:35:43 UTC, Jonathan Marler wrote:
 Any reason why "alias this" doesn't work at the module level?  
 If I recall correctly, a module is really just a "class" under 
 the hood, but when I tried to use it I got:

 Error: alias this can only be a member of aggregate, not module 
 <module-name>
It sort of does... almost. module test3; void testfun1() { } void testfun2() { } ------------------------------------------ module test2; class Test { public import test3; } ------------------------------------------ module test1; import test2; void main() { Test.test3.testfun1(); //Ok Test.test3.testfun2(); //Ok import std.stdio; import test3; assert(&Test.test3.testfun1 == &testfun1); //Passes //What? Test.testfun1(); Error: no property 'testfun1' for type 'test2.Test', did you mean 'testfun1'? } If you add this alias to Test then it will work as expected: alias testfun1 = test3.testfun1;
May 04 2017
parent Steven Schveighoffer <schveiguy yahoo.com> writes:
On 5/5/17 3:37 AM, Meta wrote:
     //What?
     Test.testfun1(); Error: no property 'testfun1' for type
 'test2.Test', did you mean 'testfun1'?
 }

 If you add this alias to Test then it will work as expected:

 alias testfun1 = test3.testfun1;
Yeah, I'm not sure public importing inside a class/struct is intended to do what you expect. The spec says "All symbols from a publicly imported module are also aliased in the importing module". But it doesn't say anything explicitly about public importing inside a class/struct. -Steve
May 05 2017