Re: How to group similar member functions from different classes?
On Friday, 15 July 2016 at 17:25:23 UTC, cy wrote: On Monday, 20 June 2016 at 16:39:54 UTC, Marc Schütz wrote: Untested: Seems to only work if A and B are both defined in the same file as Foos (defeating the purpose). Putting A and B in a.d and b.d respectively gives me these errors: a.d(2): Error: undefined identifier 'Foos' a.d(2): Error: mixin a.A.Foos!() is not defined b.d(2): Error: undefined identifier 'Foos' b.d(2): Error: mixin b.B.Foos!() is not defined I also tried switching it around, like // b.d import foos Foos; class B { mixin Foos; } but that of course gives the error: foos.d(4): Error: undefined identifier 'A' b.d(3): Error: mixin b.B.Foos!() error instantiating since you can't do a static if(typeof(this) == A) without importing A from a somehow. (you can do else static if(typeof(this) == B) without importing B though, since it does the branch for A first) I think a mixin here is just required, because you can't use an identifier before it's defined, even at compile time. Honestly, I have yet to find a use for mixin templates. It works if you add forward declarations for the classes: import a, b; class A; class B; mixin template Foos() { static if(is(typeof(this) == A)) void foo() { /* implementation for A */ } static if(is(typeof(this) == B)) void foo() { /* implementation for B */ } }
Re: How to group similar member functions from different classes?
On Monday, 20 June 2016 at 16:39:54 UTC, Marc Schütz wrote: Untested: Seems to only work if A and B are both defined in the same file as Foos (defeating the purpose). Putting A and B in a.d and b.d respectively gives me these errors: a.d(2): Error: undefined identifier 'Foos' a.d(2): Error: mixin a.A.Foos!() is not defined b.d(2): Error: undefined identifier 'Foos' b.d(2): Error: mixin b.B.Foos!() is not defined I also tried switching it around, like // b.d import foos Foos; class B { mixin Foos; } but that of course gives the error: foos.d(4): Error: undefined identifier 'A' b.d(3): Error: mixin b.B.Foos!() error instantiating since you can't do a static if(typeof(this) == A) without importing A from a somehow. (you can do else static if(typeof(this) == B) without importing B though, since it does the branch for A first) I think a mixin here is just required, because you can't use an identifier before it's defined, even at compile time. Honestly, I have yet to find a use for mixin templates.
Re: How to group similar member functions from different classes?
Untested: // foo.d import a, b; mixin template Foos { static if(is(typeof(this) == A)) void foo() { /* implementation for A */ } static if(is(typeof(this) == B)) void foo() { /* implementation for B */ } } // a.d import foo; class A { mixin Foos; } // b.d import foo; class B { mixin Foos; } You must not have static constructors in any of these modules because you'd likely get problems with circular initialization.
Re: How to group similar member functions from different classes?
On Saturday, 18 June 2016 at 07:03:25 UTC, cy wrote: So how would you do it? Defining A.foo, B.foo, etc in one place, and A.bar, B.bar, etc in another? No such thing in D. But you can always be creative and use an overloaded helper function containing the actual implementation if you want to group the code by functionality and not by type: class A { int foo() { return doFoo(this); } class B : A { int foo() { return doFoo(this); } ... void doFoo(A a) { ... } void doFoo(B b) { ... } If you need full access to the members, the helpers would need to be in the same module, otherwise you can put them into a separate helper.
Re: How to group similar member functions from different classes?
On Saturday, 18 June 2016 at 07:03:25 UTC, cy wrote: So how would you do it? Defining A.foo, B.foo, etc in one place, and A.bar, B.bar, etc in another? The only thing I've been able to figure is a horrible hack, where your member functions are something like // off in define_foos.d template foo_for(T) { static if(is(T == A)) { enum foo_for = q{ int foo () { return bar+42; } }; } else static if(is(T == B)) { enum foo_for = q{ int foo () { return bar+23; } }; } } // in classes.d import define_foos: foo_for; struct A { int bar; mixin(foo_for!A); } struct B { int bar; mixin(foo_for!B); } // etc void main() { import std.stdio; A a = A(0); B b = B(1); writeln(b.foo()); writeln(a.foo()); }
How to group similar member functions from different classes?
When I define functions like: class A { abstract void format(...) {...} } class B : A { void format(...) {...} } class C : A { void format(...) {...} } and so on, often these different member functions all share a lot in common. Maybe they are the only ones that require formatting modules, that do I/O, that do string manipulation, that sort of thing. But if I made a second function, say for instance clone() or replaceWithDucks(), it too might import a lot of modules, and perform a lot of logic. And there may be many, many different types of object here. In C++ I could forward declare the member functions, then put all "::format(...)" member functions together in their own source file, making everything pretty neat and tidy. How do I do that in D? As near as I can tell, you can only define member functions inside the class definition itself, and you can't add to that definition piece-wise like // file 1 class A ... { void format(...) { ... } } ... // file 2 class A ... { void doathing() { ... } } ... So how would you do it? Defining A.foo, B.foo, etc in one place, and A.bar, B.bar, etc in another?