digitalmars.D.learn - Cascading, variable mixins
- Slavisa Radic (50/50) Oct 01 2007 Hello Folks,
- Jarrett Billingsley (12/52) Oct 01 2007 Try something like..
- Slavisa Radic (16/16) Oct 01 2007 hmm, ok, now we managed to extend the class without touching it. But unf...
- BCS (18/60) Oct 01 2007 I haven't tried it but this may work
Hello Folks, I would like to augment a mixin with another mixin, which gets augmented by another mixin...and so forth The most important design goal is, how to pass a mixin as parameter and the class which gets augmented by the mixin does not has to import the mixin. My overall-goal is to be able to extend functionality of a class from outside, without the need to touch the class itself (kind of inter-type-declaration). I managed to pass a template as an alias parameter to the class which was going to be augmented. This class was able to mix it in. Next i tried to do the same with the template which gets mixed in. I parameterized it with an alias-parameter, and used the parameter as mixin. However, this doesn't work. In order to parameterize the template, I had to instantiate it. This instantiated template then could not get mixed in in the class, as it was no template-name any-more. To illustrate this a little bit: --------------------------- import std.stdio; class A(alias T) { mixin T; } ------------------------- module b; import std.stdio; template B(alias T) { public void foo() { writefln("This is template-code from Template B"); } mixin T; } ------------------------------------------------------------------- module b2; template B2() { public void bar() { writefln("And This is Code from a different Template, namely Template B2"); } } -------------------------------- private import a; private import b; private import b2; int main(char[][] args) { A! ( B! (B2) ) a = new A! ( B! (B2) ) (); a.foo(); a.bar(); return 0; } -------------------------------------------- Compiling this will result in the following error: a.d:5: mixin T is not a template And it's true. It is really no template as it gets instantiated in the main-function. The problem is, how to parameterize B without instantiating it? I would realy apreciate it If somebody would have a solution for this, as I need it for my Master-Thesis. So please do not post comments like "why should somebody do such stuff" - there are people - e.g. me ;-)
Oct 01 2007
"Slavisa Radic" <konfusious gmx.de> wrote in message news:fdqo5g$2prv$1 digitalmars.com...To illustrate this a little bit: --------------------------- import std.stdio; class A(alias T) { mixin T; } ------------------------- module b; import std.stdio; template B(alias T) { public void foo() { writefln("This is template-code from Template B"); } mixin T; } ------------------------------------------------------------------- module b2; template B2() { public void bar() { writefln("And This is Code from a different Template, namely Template B2"); } } -------------------------------- private import a; private import b; private import b2; int main(char[][] args) { A! ( B! (B2) ) a = new A! ( B! (B2) ) (); a.foo(); a.bar(); return 0; } --------------------------------------------Try something like.. class A(alias T, Args...) { mixin T!(Args); } ... auto a = new A!(B, B2)(); a.foo(); a.bar(); WOrks for me :)
Oct 01 2007
hmm, ok, now we managed to extend the class without touching it. But unfortunatly, I forgot to mention that the templates shouldn't be touched from outside either. So the goal is to build a set of refinements of classes, which then should be plugged together in the main-method, in order to produce desired classes. Your proposal was to make the amount of template-parameters for the target-class variadic. That leads to the necessity of changing the templates (template b) parameter-list. What i'm looking for, is a way to build chains of mixins with arbitrary depth. The proposed solution is just of depth 2. Your Solution: a mixes in b b mixes in b2 b mixes in b3 b mixes in b4 and so forth... But I'm looking for a way to do: a mixes in b b mixes in b2 b2 mixes in b3 b3 mixes in b4 and so forth But thanks for your interesting suggestion.
Oct 01 2007
Reply to Slavisa,I haven't tried it but this may work template B(alias T) { template inner() { public void foo() { writefln("This is template-code from Template B"); } mixin T; } } class A(alias T) { mixin T.inner; } auto a = new A! ( B!(B2) ) ();To illustrate this a little bit:--------------------------- import std.stdio; class A(alias T) { mixin T; } ------------------------- module b; import std.stdio; template B(alias T) { public void foo() { writefln("This is template-code from Template B"); } mixin T; } ------------------------------------------------------------------- module b2; template B2() { public void bar() { writefln("And This is Code from a different Template, namely Template B2"); } } -------------------------------- private import a; private import b; private import b2; int main(char[][] args) { A! ( B! (B2) ) a = new A! ( B! (B2) ) (); a.foo(); a.bar(); return 0; } --------------------------------------------
Oct 01 2007