www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - What about some standard mixins

reply J Anderson <REMOVEanderson badmama.com.au> writes:
Just a though, what if we had some standard mixins in one of the 
standard libraries.  I mean for thing like vectors you generally write 
up the same code.  Something like:

template arrayMixin(structName, type, value)
{
     type opIndex(int i) { ... }
...ect...
}

Then in your own module you could write:

struct myArray(type)
{
      arrayMixin!(myArray, type, values); //Note that I don't think 
values will work ATM.

      type [] values;

}

Then you could overload any functions you wish to change.   I'm sure 
there are heaps of these types of common method groups.

It would be really helpful for lazy programmers like me.

I should add that this is basicly what classes are meant to do but for 
things like vectors you want a "light-class" which happens to be a 
struct in D.  I guess there could be a class version as well.

-- 
-Anderson: http://badmama.com.au/~anderson/
May 25 2004
next sibling parent reply "Matthew" <matthew.hat stlsoft.dot.org> writes:
There'll be some standard ones in DTL, although they'll necessarily pertain to
containers.

As a general point, I'm still a little nervous about the potential ubituity of
mixins, as supported by their current implementation, but I guess we'll just
have
to suck it and see.

"J Anderson" <REMOVEanderson badmama.com.au> wrote in message
news:c90q9p$2t6k$3 digitaldaemon.com...
 Just a though, what if we had some standard mixins in one of the
 standard libraries.  I mean for thing like vectors you generally write
 up the same code.  Something like:

 template arrayMixin(structName, type, value)
 {
      type opIndex(int i) { ... }
 ...ect...
 }

 Then in your own module you could write:

 struct myArray(type)
 {
       arrayMixin!(myArray, type, values); //Note that I don't think
 values will work ATM.

       type [] values;

 }

 Then you could overload any functions you wish to change.   I'm sure
 there are heaps of these types of common method groups.

 It would be really helpful for lazy programmers like me.

 I should add that this is basicly what classes are meant to do but for
 things like vectors you want a "light-class" which happens to be a
 struct in D.  I guess there could be a class version as well.

 -- 
 -Anderson: http://badmama.com.au/~anderson/

May 25 2004
parent reply "Walter" <newshound digitalmars.com> writes:
"Matthew" <matthew.hat stlsoft.dot.org> wrote in message
news:c90ql8$2u1r$1 digitaldaemon.com...
 As a general point, I'm still a little nervous about the potential

 mixins, as supported by their current implementation, but I guess we'll

 to suck it and see.

?
May 25 2004
next sibling parent reply "Matthew" <matthew.hat stlsoft.dot.org> writes:
Nothing specific. Just a feeling at the moment.

Sorry to be vague.

"Walter" <newshound digitalmars.com> wrote in message
news:c910ga$4fc$1 digitaldaemon.com...
 "Matthew" <matthew.hat stlsoft.dot.org> wrote in message
 news:c90ql8$2u1r$1 digitaldaemon.com...
 As a general point, I'm still a little nervous about the potential

 mixins, as supported by their current implementation, but I guess we'll

 to suck it and see.

?

May 25 2004
next sibling parent reply J Anderson <REMOVEanderson badmama.com.au> writes:
Matthew wrote:

Nothing specific. Just a feeling at the moment.

Sorry to be vague.
  

syntax. I mean essentially a mixin is a copy/paste tool. -- -Anderson: http://badmama.com.au/~anderson/
May 26 2004
parent reply Norbert Nemec <Norbert.Nemec gmx.de> writes:
J Anderson wrote:

 Matthew wrote:
 
Nothing specific. Just a feeling at the moment.

Sorry to be vague.
  

syntax. I mean essentially a mixin is a copy/paste tool.

So are templates. So what? D has a powerful compile-time meta-language. The purpose of this meta-language is to do all kinds of copy-and-paste operations before the real compilation is started. Unlike the CPP, this source-code processing cannot by fully split out of the compiling process. Unlike CPP, it uses the same namespace as the compiler, but it offers most of the power of the CPP. C++ had two steps of "preprocessing": first the CPP, then the template instatiation (which is basically lots of copy-and-paste as well) then the real compilation. Mixins basically *are* macros with a different syntax. But through that syntax, they are far better integrated into the language itself then CPP-macros ever were.
May 26 2004
parent reply J Anderson <REMOVEanderson badmama.com.au> writes:
Norbert Nemec wrote:

J Anderson wrote:

  

Matthew wrote:

    

Nothing specific. Just a feeling at the moment.

Sorry to be vague.
 

      

syntax. I mean essentially a mixin is a copy/paste tool.

So are templates. So what? D has a powerful compile-time meta-language. The purpose of this meta-language is to do all kinds of copy-and-paste operations before the real compilation is started. Unlike the CPP, this source-code processing cannot by fully split out of the compiling process. Unlike CPP, it uses the same namespace as the compiler, but it offers most of the power of the CPP. C++ had two steps of "preprocessing": first the CPP, then the template instatiation (which is basically lots of copy-and-paste as well) then the real compilation. Mixins basically *are* macros with a different syntax. But through that syntax, they are far better integrated into the language itself then CPP-macros ever were.

want to go. I'm not quite sure where yet. -- -Anderson: http://badmama.com.au/~anderson/
May 26 2004
next sibling parent reply Norbert Nemec <Norbert.Nemec gmx.de> writes:
J Anderson wrote:

 Sure but I've a feeling that they may lead to some places where we don't
 want to go.  I'm not quite sure where yet.

Guess, they are only the next step on the trip that was started when templates were introduced to C++: A hell of a ride without safety-belt: We have that meta-language of D that does not have any type-check at all. (I.e.: template arguments are basically just fit in via copy&paste) The checks that are done on a template are nothing but syntax checks needed for parsing the code. A stand-alone template cannot be checked. It cannot be said correct or incorrect, this always depends on its use. There is no interface of a template. Any C/C++/D programmer feels awkward using a weakly-typed language. I have been using Matlab for a while now, and it still feels strange to define functions without being able to specify what type the arguments are. I don't know where this read will lead us. Maybe it really is the wrong direction. Anyhow, it was not started with mixins but with templates.
May 27 2004
parent reply J Anderson <REMOVEanderson badmama.com.au> writes:
Norbert Nemec wrote:

J Anderson wrote:
  

Sure but I've a feeling that they may lead to some places where we don't
want to go.  I'm not quite sure where yet.
    

I don't know where this read will lead us. Maybe it really is the wrong direction. Anyhow, it was not started with mixins but with templates.

-- -Anderson: http://badmama.com.au/~anderson/
May 27 2004
parent Norbert Nemec <Norbert.Nemec gmx.de> writes:
J Anderson wrote:

 Norbert Nemec wrote:
 
J Anderson wrote:
  

Sure but I've a feeling that they may lead to some places where we don't
want to go.  I'm not quite sure where yet.
    

I don't know where this read will lead us. Maybe it really is the wrong direction. Anyhow, it was not started with mixins but with templates.


OK, that was in the old C era. Now, with D, we thought we had left that bag of problems behind by retiring the CPP. Anyhow, templates were left in place, and these already contain the whole complexity of an untyped compile-time language. Mixins only are a completion to templates. Mixins did not open the box of Pandora. That box was opened by templates some while ago. Mixins only make the problems more obvious.
May 27 2004
prev sibling parent reply Antti =?iso-8859-1?Q?Syk=E4ri?= <jsykari gamma.hut.fi> writes:
I've the same kinda feeling.  It feels like macros with a different
syntax.  I mean essentially a mixin is a copy/paste tool.

So are templates. So what? D has a powerful compile-time meta-language. The purpose of this meta-language is to do all kinds of copy-and-paste operations before the real compilation is started. Unlike the CPP, this source-code processing cannot by fully split out of the compiling process. Unlike CPP, it uses the same namespace as the compiler, but it offers most of the power of the CPP. C++ had two steps of "preprocessing": first the CPP, then the template instatiation (which is basically lots of copy-and-paste as well) then the real compilation. Mixins basically *are* macros with a different syntax. But through that syntax, they are far better integrated into the language itself then CPP-macros ever were.

want to go. I'm not quite sure where yet.

Situations like this, I always like to quote Dr. Graham... "There is one thing more important than brevity to a hacker: being able to do what you want. In the history of programming languages a surprising amount of effort has gone into preventing programmers from doing things considered to be improper. This is a dangerously presumptuous plan. How can the language designer know what the programmer is going to need to do? I think language designers would do better to consider their target user to be a genius who will need to do things they never anticipated, rather than a bumbler who needs to be protected from himself. The bumbler will shoot himself in the foot anyway. You may save him from referring to variables in another package, but you can't save him from writing a badly designed program to solve the wrong problem, and taking forever to do it." http://www.paulgraham.com/popular.html Besides, aren't inline functions a kind of copy/paste tool as well? Not to mention *inheritance*! -Antti -- I will not be using Plan 9 in the creation of weapons of mass destruction to be used by nations other than the US.
May 27 2004
parent Norbert Nemec <Norbert.Nemec gmx.de> writes:
Antti Sykäri wrote:

 Besides, aren't inline functions a kind of copy/paste tool as well? Not
 to mention *inheritance*!

True, but they are rather safe in terms of semantics. They have limited potential compared to mixins, which don't fix much semantics at all.
May 27 2004
prev sibling parent "Ivan Senji" <ivan.senji public.srce.hr> writes:
"Matthew" <matthew.hat stlsoft.dot.org> wrote in message
news:c9125r$6tn$1 digitaldaemon.com...
 Nothing specific. Just a feeling at the moment.

 Sorry to be vague.

I had a feeling too but i know what it is! We can mixin declarations (of varaibles, functions, structs, and classes) and it is ok, but what about mixing of other types of code. for example: <EXAMPLE1> template mytest(alias a, alias b) { //some test on a and b, possibly something complex a==b; // :) } int main(char[][] args) { float x=3,y=3; if(mixin mytest!(x,y)) {//... } } </EXAMPLE1> or <EXAMPLE2> template callfunc(alias b) { .b(); } class A { int func(){return 0;} } int main(char[][] args) { A a = new A(); a mixin callfunc!(func); } </EXAMPLE2> Probbably like all of my crazzy ideas this one is crazzy too :) But if we have language support of copy-paste why not copy-paste something else.
 "Walter" <newshound digitalmars.com> wrote in message
 news:c910ga$4fc$1 digitaldaemon.com...
 "Matthew" <matthew.hat stlsoft.dot.org> wrote in message
 news:c90ql8$2u1r$1 digitaldaemon.com...
 As a general point, I'm still a little nervous about the potential

 mixins, as supported by their current implementation, but I guess



 just have
 to suck it and see.

?


May 27 2004
prev sibling parent Roberto Mariottini <Roberto_member pathlink.com> writes:
In article <c910ga$4fc$1 digitaldaemon.com>, Walter says...
"Matthew" <matthew.hat stlsoft.dot.org> wrote in message
news:c90ql8$2u1r$1 digitaldaemon.com...
 As a general point, I'm still a little nervous about the potential

 mixins, as supported by their current implementation, but I guess we'll

 to suck it and see.

?

I can add what I've thought when I've just finished to read the mixins specification: mixins are something I just don't want to need to use. But if I'll need them I'll use them without worring. I remember that I felt the same when I first read about templates. Maybe we just have to wait to be used to them, first. Ciao PS: I dont' know if this is standard english. Maybe I've used some proprietary extensions...
May 26 2004
prev sibling next sibling parent J Anderson <REMOVEanderson badmama.com.au> writes:
J Anderson wrote:

 I should add that this is basicly what classes are meant to do but for 
 things like vectors you want a "light-class" which happens to be a 
 struct in D.  I guess there could be a class version as well.

And a class version could easily be done like: class vector(type) { arrayMixin!(vector, type, values); ... } So I guess there wouldn't be any redundancy problems. -- -Anderson: http://badmama.com.au/~anderson/
May 25 2004
prev sibling next sibling parent reply Kevin Bealer <Kevin_member pathlink.com> writes:
In article <c90q9p$2t6k$3 digitaldaemon.com>, J Anderson says...
Just a though, what if we had some standard mixins in one of the 
standard libraries.  I mean for thing like vectors you generally write 
up the same code.  Something like:

template arrayMixin(structName, type, value)
{
     type opIndex(int i) { ... }
...ect...
}

Then in your own module you could write:

struct myArray(type)
{
      arrayMixin!(myArray, type, values); //Note that I don't think 
values will work ATM.

      type [] values;

}

I think this can work, but I think "values" has to be part of the mixin. I don't think a mixin can refer to other stuff "near it" in the class. The class can see into the mixin, but not the other way. Which you can do with a macro of course; you can use the variable "i" in a macro and it will "pick up" a local variable with that name. This is kind of like the coming-from-basic programmers who create a global "int i" so they don't need to type "int" everywhere. Kevin
May 26 2004
parent reply Norbert Nemec <Norbert.Nemec gmx.de> writes:
Kevin Bealer wrote:

 In article <c90q9p$2t6k$3 digitaldaemon.com>, J Anderson says...
Just a though, what if we had some standard mixins in one of the
standard libraries.  I mean for thing like vectors you generally write
up the same code.  Something like:

template arrayMixin(structName, type, value)
{
     type opIndex(int i) { ... }
...ect...
}

Then in your own module you could write:

struct myArray(type)
{
      arrayMixin!(myArray, type, values); //Note that I don't think
values will work ATM.

      type [] values;

}

I think this can work, but I think "values" has to be part of the mixin. I don't think a mixin can refer to other stuff "near it" in the class. The class can see into the mixin, but not the other way.

Why that? There even is an example in the specs that does just that: ----------------------- Mixins can parameterize symbols using alias parameters: template Foo(alias b) { int abc() { return b; } } void test() { int y = 8; mixin Foo!(y); assert(abc() == 8); } ------------------------
May 26 2004
next sibling parent reply "Kris" <someidiot earthlink.dot.dot.dot.net> writes:
"Norbert Nemec"  wrote
 Why that? There even is an example in the specs that does just that:

 -----------------------
  Mixins can parameterize symbols using alias parameters:
         template Foo(alias b)
         {
             int abc() { return b; }
         }

         void test()
         {
             int y = 8;
             mixin Foo!(y);
             assert(abc() == 8);
         }
 ------------------------

Yes, but just think how confusing such code would become on a large-scale project ... to my mind this is cruel abuse of the language syntax, and smacks of anti-OO. The fact that I can drive a car doesn't make it a good scuba companion <g>
May 26 2004
parent reply Norbert Nemec <Norbert.Nemec gmx.de> writes:
Kris wrote:

 "Norbert Nemec"  wrote
 Why that? There even is an example in the specs that does just that:

 -----------------------
  Mixins can parameterize symbols using alias parameters:
         template Foo(alias b)
         {
             int abc() { return b; }
         }

         void test()
         {
             int y = 8;
             mixin Foo!(y);
             assert(abc() == 8);
         }
 ------------------------

Yes, but just think how confusing such code would become on a large-scale project ... to my mind this is cruel abuse of the language syntax, and smacks of anti-OO. The fact that I can drive a car doesn't make it a good scuba companion <g>

Of course you can write the worst spaghetti code with mixins. They just are an extremely powerful tool that allows you to do much more than you really need. It is up to the programmer to use that tool well. I don't think access like in the example above is generally a bad thing. It may well be that it really helps you a lot, depending on what you want to do with the mixin. I think the scary thing about mixins is, that they are not bound to a certain programming concept. "Mixin" may stand for * a chunk of code to be used in a function * a mostly independant part of a class, where mixin is similar to inheritance * a certain kind of a class member (like a signal, a slot, a property, whatever * a complete source file to be used like CPP #include * a certain aspect of a class and probably many other things that may not even be invented yet. Mixins are a very new language concept and nobody knows yet how they should be used well in a library. It will certainly take some time before we have enough experience with mixins to really make use of them and before we can say "This is good programming practice" or "That may lead to problems".
May 26 2004
parent reply "Kris" <someidiot earthlink.dot.dot.dot.net> writes:
"Norbert Nemec" wrote
 I think the scary thing about mixins is, that they are not bound to a
 certain programming concept.

That is the case with D mixins.
 Mixins are a very new language concept and nobody knows yet how they

 be used well in a library. It will certainly take some time before we have
 enough experience with mixins to really make use of them and before we can
 say "This is good programming practice" or "That may lead to problems".

Mixins are certainly new to D, but have been around for ages elsewhere (Objective-C is a good example, although the concept is narrower). It might be useful for someone with reasonable experience in those other languages to set some guidelines for the uninitiated?
May 26 2004
parent reply Norbert Nemec <Norbert.Nemec gmx.de> writes:
Kris wrote:

 "Norbert Nemec" wrote
 I think the scary thing about mixins is, that they are not bound to a
 certain programming concept.

That is the case with D mixins.
 Mixins are a very new language concept and nobody knows yet how they

 be used well in a library. It will certainly take some time before we
 have enough experience with mixins to really make use of them and before
 we can say "This is good programming practice" or "That may lead to
 problems".

Mixins are certainly new to D, but have been around for ages elsewhere (Objective-C is a good example, although the concept is narrower). It might be useful for someone with reasonable experience in those other languages to set some guidelines for the uninitiated?

I'm talking only about D mixins, these are the only ones I know. As you say, in other languages "mixin" refers to a narrower concept. Maybe, D should have used a new name to make clear that this is something new. They may be used to do what other languages do with their mixins. They may be used for many of the uses where C uses macros. But they may probably also be used for completely new purposes. If you want to want to transport programming guidelines from Objective-C to D, you will most certainly restrict mixins to a fraction of their real power. Of course, the standard library should only use mixins for well-known and well-investigated purposes, but whether these match with the concept of Objective-C mixins should probably be left open for the moment.
May 26 2004
parent "Kris" <someidiot earthlink.dot.dot.dot.net> writes:
Please don't get me wrong Norbert: I'm not trying to split hairs or be
argumentative.

I suppose I have a similar vague feeling about D mixins that Matthew noted,
regarding what he described as their "potential ubiquity". Perhaps that
mixin example from the documentation just rubs me the wrong way (with alias
and template "mixed-in", just for good measure, it's like a vulgar soup) ...
not exactly what one might expect in terms of a "teach by example" approach
<g>

I guess that's just me though ...

- Kris


"Norbert Nemec" <Norbert.Nemec gmx.de> wrote in message
news:c92v2i$1gq$1 digitaldaemon.com...
 Kris wrote:

 "Norbert Nemec" wrote
 I think the scary thing about mixins is, that they are not bound to a
 certain programming concept.

That is the case with D mixins.
 Mixins are a very new language concept and nobody knows yet how they

 be used well in a library. It will certainly take some time before we
 have enough experience with mixins to really make use of them and



 we can say "This is good programming practice" or "That may lead to
 problems".

Mixins are certainly new to D, but have been around for ages elsewhere (Objective-C is a good example, although the concept is narrower). It might be useful for someone with reasonable experience in those other languages to set some guidelines for the uninitiated?

I'm talking only about D mixins, these are the only ones I know. As you

 in other languages "mixin" refers to a narrower concept. Maybe, D should
 have used a new name to make clear that this is something new. They may be
 used to do what other languages do with their mixins. They may be used for
 many of the uses where C uses macros. But they may probably also be used
 for completely new purposes.

 If you want to want to transport programming guidelines from Objective-C

 D, you will most certainly restrict mixins to a fraction of their real
 power.

 Of course, the standard library should only use mixins for well-known and
 well-investigated purposes, but whether these match with the concept of
 Objective-C mixins should probably be left open for the moment.

May 26 2004
prev sibling parent reply Kevin Bealer <Kevin_member pathlink.com> writes:
In article <c92j01$2fq5$1 digitaldaemon.com>, Norbert Nemec says...
Kevin Bealer wrote:

 In article <c90q9p$2t6k$3 digitaldaemon.com>, J Anderson says...
Just a though, what if we had some standard mixins in one of the
standard libraries.  I mean for thing like vectors you generally write
up the same code.  Something like:

template arrayMixin(structName, type, value)
{
     type opIndex(int i) { ... }
...ect...
}

Then in your own module you could write:

struct myArray(type)
{
      arrayMixin!(myArray, type, values); //Note that I don't think
values will work ATM.

      type [] values;

}

I think this can work, but I think "values" has to be part of the mixin. I don't think a mixin can refer to other stuff "near it" in the class. The class can see into the mixin, but not the other way.

Why that? There even is an example in the specs that does just that: ----------------------- Mixins can parameterize symbols using alias parameters: template Foo(alias b) { int abc() { return b; } } void test() { int y = 8; mixin Foo!(y); assert(abc() == 8); } ------------------------

I don't have a problem with those semantics at all. I was thinking of something like this:
-----------------------
 Mixins can parameterize symbols using alias parameters: 
        template Foo(alias b)
        {
            // The caller won't mind if I borrow "Z".
            int abc() { return b + Z; }
        }

        void test()
        {
            int y = 8;
            int Z = 99;  // The mixin might want one of these.
            mixin Foo!(y);
            assert(abc() == 8);
        }
------------------------

.. Where anything can bleed in or out of the mixin. Kevin
May 26 2004
parent reply Sean Kelly <sean f4.ca> writes:
In article <c930sq$4c4$1 digitaldaemon.com>, Kevin Bealer says...
I don't have a problem with those semantics at all.  I was thinking of something
like this:

-----------------------
 Mixins can parameterize symbols using alias parameters: 
        template Foo(alias b)
        {
            // The caller won't mind if I borrow "Z".
            int abc() { return b + Z; }
        }

        void test()
        {
            int y = 8;
            int Z = 99;  // The mixin might want one of these.
            mixin Foo!(y);
            assert(abc() == 8);
        }
------------------------

.. Where anything can bleed in or out of the mixin.

This is kind of a special case, as it only works because the mixin is a template and Z is defined at the POI. Since the template can't stand on its own, it's reasonable to assume that it's designed specifically to be a mixin and carries with it special requirements. Since this would likely not happen by accident, I'd consider this a feature of mixins rather than a flaw.
May 26 2004
parent reply Kevin Bealer <Kevin_member pathlink.com> writes:
In article <c932li$77f$1 digitaldaemon.com>, Sean Kelly says...
In article <c930sq$4c4$1 digitaldaemon.com>, Kevin Bealer says...
I don't have a problem with those semantics at all.  I was thinking of something
like this:

-----------------------
 Mixins can parameterize symbols using alias parameters: 
        template Foo(alias b)
        {
            // The caller won't mind if I borrow "Z".
            int abc() { return b + Z; }
        }

        void test()
        {
            int y = 8;
            int Z = 99;  // The mixin might want one of these.
            mixin Foo!(y);
            assert(abc() == 8);
        }
------------------------

.. Where anything can bleed in or out of the mixin.

This is kind of a special case, as it only works because the mixin is a template and Z is defined at the POI. Since the template can't stand on its own, it's reasonable to assume that it's designed specifically to be a mixin and carries with it special requirements. Since this would likely not happen by accident, I'd consider this a feature of mixins rather than a flaw.

Er.. perhaps I should mention that I was under the impression that the above "poor case" was actually already not supported. Is it legal now? [I could try to compile, but that won't tell me if it's legal, only if it works.] Kevin
May 26 2004
parent reply "Ivan Senji" <ivan.senji public.srce.hr> writes:
"Kevin Bealer" <Kevin_member pathlink.com> wrote in message
news:c93uco$1fab$1 digitaldaemon.com...
 In article <c932li$77f$1 digitaldaemon.com>, Sean Kelly says...
In article <c930sq$4c4$1 digitaldaemon.com>, Kevin Bealer says...
I don't have a problem with those semantics at all.  I was thinking of



like this:

-----------------------
 Mixins can parameterize symbols using alias parameters:
        template Foo(alias b)
        {
            // The caller won't mind if I borrow "Z".
            int abc() { return b + Z; }
        }

        void test()
        {
            int y = 8;
            int Z = 99;  // The mixin might want one of these.
            mixin Foo!(y);
            assert(abc() == 8);
        }
------------------------

.. Where anything can bleed in or out of the mixin.

This is kind of a special case, as it only works because the mixin is a


and Z is defined at the POI.  Since the template can't stand on its own,


reasonable to assume that it's designed specifically to be a mixin and


with it special requirements.  Since this would likely not happen by


I'd consider this a feature of mixins rather than a flaw.

Er.. perhaps I should mention that I was under the impression that the

 "poor case" was actually already not supported.  Is it legal now?  [I

 to compile, but that won't tell me if it's legal, only if it works.]

 Kevin

I tried it and it works, it throws the assertion failiure because 8+99 != 8 I don't see a reason why this shouldn't work? Mixin makes sence only when it gets mixed in, and why shouldn't it require Z to be defined in the location where it is mixed in?
May 27 2004
parent reply Kevin Bealer <Kevin_member pathlink.com> writes:
In article <c9459p$1pln$1 digitaldaemon.com>, Ivan Senji says...
..
I tried it and it works, it throws the assertion failiure because 8+99 != 8
I don't see a reason why this shouldn't work? Mixin makes sence only when
it gets mixed in, and why shouldn't it require Z to be defined in the
location where
it is mixed in?

You're probably right. My objection was that you have no idea where the variables are coming from when you write the mixin. If you mention "x" you don't know what type it is, whether it is part of the module or the current class or what not. I was thinking that if the spelling of the variable was off, the mixin could attach itself to a "global variable" in any module. But I guess D doesn't having any data items at larger than module scope, so it shouldn't be a big deal. Just another matter of programmer judgement. Kevin
May 27 2004
parent reply EricAnderton at yahoo dot com <EricAnderton_member pathlink.com> writes:
I was thinking that if the spelling of the variable was off, the mixin could
attach itself to a "global variable" in any module.  But I guess D doesn't
having any data items at larger than module scope, so it shouldn't be a big
deal.  Just another matter of programmer judgement.

If you guys don't mind, I'd like to chime in here. :) First of all, I couldn't agree more with this sentiment. There is a huge potential for bugs and scope problems in the misuse of mixins. I went about trying to investigate the problem, and try to uncover where this might cause problems. I wound up digging up some interesting bugs... I've always felt that the 'borrowing' feature (as Kevin put it) of mixins as more of a side-effect of plonking a mixin into a given namespace than an intentional feature. It's probably the kind of thing that should be used carefully, much like fallthroughs on switch statements or treating an int like a bool (checking for i!=0 instead of i>0). So I thought a little bit about what would be best practice for mixins given the example so far. I figured that a good solution for the 'borrowing' problem is just to do it as little as possible, whenever possible. For example, declaring a mixin type as requiring all fields it uses as template parameters, rather than just blindly borrowing one by name. template Foo(alias b,alias Z) { int abc() { return b + Z; } } void test() { int y = 8; int Z = 99; mixin Foo!(y,Z); printf("abc() = %d\n",abc()); } The mixin responds with 'abc() = 107' and is much harder to misuse, nor will it generate any odd side-effects. I would also advocate declaring any variable the mixin uses wherever possible, so as to minimize trouble using a given mixin (treating it kind of like a local class instance w/o a namespace): template Foo(alias b) { int Z; int abc() { return b + Z; } } However, defining the mixin template like this yields some strange things, none of which are expected: void test(){ int y = 8; mixin Foo!(y); // mixin declares 'Z' internally printf("abc() = %d\n",abc()); } The above prints out garbage since Foo.int is never initalized. Even setting an initalizer in the template (eg: int Z = whatever; ) doesn't work either. (is this a bug in V.90?) void test(){ int y = 8; mixin Foo!(y); Z = 88; // try to initalize 'Z' printf("abc() = %d\n",abc()); } Why this fails I'll probably never know. The compiler seems to understand that 'Z' is defined in the current scope, but again, Foo.Z never gets the assigned value. void test(){ int y = 8; mixin Foo!(y); int Z = 88; // try to define and initalize 'Z' printf("abc() = %d\n",abc()); } I'm pretty sure this shouldn't even compile. Once again, garbage is produced in the output.
May 27 2004
parent reply Kevin Bealer <Kevin_member pathlink.com> writes:
In article <c95h4u$1jbj$1 digitaldaemon.com>, EricAnderton at yahoo dot com
says...
First of all, I couldn't agree more with this sentiment.  There is a huge
potential for bugs and scope problems in the misuse of mixins. I went about
trying to investigate the problem, and try to uncover where this might cause
problems.  I wound up digging up some interesting bugs...

I've always felt that the 'borrowing' feature (as Kevin put it) of mixins as
more of a side-effect of plonking a mixin into a given namespace than an
intentional feature.  It's probably the kind of thing that should be used
carefully, much like fallthroughs on switch statements or treating an int like a
bool (checking for i!=0 instead of i>0).

So I thought a little bit about what would be best practice for mixins given the
example so far.  I figured that a good solution for the 'borrowing' problem is
just to do it as little as possible, whenever possible.  For example, declaring
a mixin type as requiring all fields it uses as template parameters, rather than
just blindly borrowing one by name.

I'm not changing my opinion here - I still think the borrowing is going to be a maintainence issue if misused ... but I just thought of a potential use for it: Essentially, mixins could borrow from *each other*. Consider if you will, a set of related mixins. SocketLike_Socket: provides a set of variables and methods that track a socket connection. CommandQueue: provides queueing operations that use the methods of SocketLike. StatsModule: provides a set of methods to store statistics, and a method to get the formatted results, DisplayStats. NullStats: provides empty methods with same interface as StatsModule, except that it doesn't provide DisplayStats. Now, the user of this library can mix-and-match to make their own Mr. Potato Head version of the socket handling library. They can include CommandQueue, which provides a framework for processing network requests. Or they can provide their own methods to replace that functionality. They can use StatsModule to get detailed statistics on the socket's communication behaviour; or they can use NullStats to eliminate statistics gathering, in which case the user can't call DisplayStats because it isnt defined. They can use SocketLike_Socket for true network communication; or they can define the associated methods to get data to and from a pipe, file, XML channel of some kind, other classes or child processes, graphical widget set. Each of these has a name like "SocketLike_wxWindows_menu_item" and provides the socket framework. Hence is realized "aspect" like programming. You can pull in whatever functionality, and put your own interface on the outside of the class. Each mixin is optional, but they talk to each other .... because the variables and methods mix. Kevin
May 27 2004
parent reply "Kris" <someidiot earthlink.dot.dot.dot.net> writes:
If I understand you correctly, you could do the same thing using
abstract-base-classes and/or Interfaces (via well documented patterns);
which would offer far more robustness than what appears to be a bunch of
loosely-bound global variables and methods ...

Just my 2 pence worth.

- Kris


"Kevin Bealer" <Kevin_member pathlink.com> wrote in message
news:c95irt$1m6g$1 digitaldaemon.com...
 In article <c95h4u$1jbj$1 digitaldaemon.com>, EricAnderton at yahoo dot

 says...
First of all, I couldn't agree more with this sentiment.  There is a huge
potential for bugs and scope problems in the misuse of mixins. I went


trying to investigate the problem, and try to uncover where this might


problems.  I wound up digging up some interesting bugs...

I've always felt that the 'borrowing' feature (as Kevin put it) of mixins


more of a side-effect of plonking a mixin into a given namespace than an
intentional feature.  It's probably the kind of thing that should be used
carefully, much like fallthroughs on switch statements or treating an int


bool (checking for i!=0 instead of i>0).

So I thought a little bit about what would be best practice for mixins


example so far.  I figured that a good solution for the 'borrowing'


just to do it as little as possible, whenever possible.  For example,


a mixin type as requiring all fields it uses as template parameters,


just blindly borrowing one by name.

I'm not changing my opinion here - I still think the borrowing is going to

 maintainence issue if misused ... but I just thought of a potential use

 Essentially, mixins could borrow from *each other*.


 Consider if you will, a set of related mixins.

 SocketLike_Socket: provides a set of variables and methods that track a

 connection.

 CommandQueue: provides queueing operations that use the methods of

 StatsModule: provides a set of methods to store statistics, and a method

 the formatted results, DisplayStats.

 NullStats: provides empty methods with same interface as StatsModule,

 that it doesn't provide DisplayStats.


 Now, the user of this library can mix-and-match to make their own Mr.

 Head version of the socket handling library.  They can include

 which provides a framework for processing network requests.  Or they can

 their own methods to replace that functionality.

 They can use StatsModule to get detailed statistics on the socket's
 communication behaviour;  or they can use NullStats to eliminate

 gathering, in which case the user can't call DisplayStats because it isnt
 defined.

 They can use SocketLike_Socket for true network communication; or they can
 define the associated methods to get data to and from a pipe, file, XML

 of some kind, other classes or child processes, graphical widget set.

 these has a name like "SocketLike_wxWindows_menu_item" and provides the

 framework.

 Hence is realized "aspect" like programming.  You can pull in whatever
 functionality, and put your own interface on the outside of the class.

 mixin is optional, but they talk to each other .... because the variables

 methods mix.

 Kevin

May 27 2004
parent reply Kevin Bealer <Kevin_member pathlink.com> writes:
In article <c95jhs$1n8c$1 digitaldaemon.com>, Kris says...
If I understand you correctly, you could do the same thing using
abstract-base-classes and/or Interfaces (via well documented patterns);
which would offer far more robustness than what appears to be a bunch of
loosely-bound global variables and methods ...

Just my 2 pence worth.

- Kris

It may be cleaner and better for many cases. But for some cases, looser semantics may be just what the doctor ordered. I think I need to take some time and play with the feature before I can give a better example. Kevin
May 27 2004
parent reply "Kris" <someidiot earthlink.dot.dot.dot.net> writes:
Yeah, you may be right.

My post perhaps came across as more negative than was intended, as I have
this nagging feeling that unfettered use of mixins may lead to hideous
convolutions. Remember those proud competitions that folk used to have for
the most convoluted usage of the CPP? Well, the hairs on the back of my neck
stand up when I think about how D mixins might enter that ring as a serious
contender <g>

- Kris


"Kevin Bealer" <Kevin_member pathlink.com> wrote in message
news:c95o7v$1u4q$1 digitaldaemon.com...
 In article <c95jhs$1n8c$1 digitaldaemon.com>, Kris says...
If I understand you correctly, you could do the same thing using
abstract-base-classes and/or Interfaces (via well documented patterns);
which would offer far more robustness than what appears to be a bunch of
loosely-bound global variables and methods ...

Just my 2 pence worth.

- Kris

It may be cleaner and better for many cases. But for some cases, looser semantics may be just what the doctor ordered. I think I need to take

 and play with the feature before I can give a better example.

 Kevin

May 27 2004
parent "Bent Rasmussen" <exo bent-rasmussen.info> writes:
 Yeah, you may be right.

 My post perhaps came across as more negative than was intended, as I have
 this nagging feeling that unfettered use of mixins may lead to hideous
 convolutions. Remember those proud competitions that folk used to have for
 the most convoluted usage of the CPP? Well, the hairs on the back of my

 stand up when I think about how D mixins might enter that ring as a

 contender <g>

If one tries not to have convoluted usage of mixins as a major design goal of ones real-life programs perhaps the problem isn't so great. ;-) Of course there's nothing preventing people from using stuff in a way they're not supposed to but then they must either know what they're doing or learn the hard way. :-)
 - Kris

May 31 2004
prev sibling next sibling parent Andy Friesen <andy ikagames.com> writes:
J Anderson wrote:

 Just a though, what if we had some standard mixins in one of the 
 standard libraries.  I mean for thing like vectors you generally write 
 up the same code.  Something like:

If there are standard-library-worthy constructs that need to be implemented this way (or merely where it is obviously the right way) then sure, but it seems backwards to say 'we need some standard mixins'. That being said, a singleton mixin, and maybe some allocators would be useful. -- andy
May 26 2004
prev sibling parent reply "davepermen" <davepermen hotmail.com> writes:
i think it would now allow to have the operators finally split up
(comparison and all the like)..

instead you mix in a set of operators for common types, so you don't have to
write everyone manually..

should be doable, not?

mixin Addable to get in opAdd, opAddAsign, and such.. mixin Comparable, for
opLess, opLEqual, opEqual, opGEqual, opGreater, opGeek..

(but of course, you have to implement then an opComparable wich handles
them..)

"J Anderson" <REMOVEanderson badmama.com.au> schrieb im Newsbeitrag
news:c90q9p$2t6k$3 digitaldaemon.com...
 Just a though, what if we had some standard mixins in one of the
 standard libraries.  I mean for thing like vectors you generally write
 up the same code.  Something like:

 template arrayMixin(structName, type, value)
 {
      type opIndex(int i) { ... }
 ...ect...
 }

 Then in your own module you could write:

 struct myArray(type)
 {
       arrayMixin!(myArray, type, values); //Note that I don't think
 values will work ATM.

       type [] values;

 }

 Then you could overload any functions you wish to change.   I'm sure
 there are heaps of these types of common method groups.

 It would be really helpful for lazy programmers like me.

 I should add that this is basicly what classes are meant to do but for
 things like vectors you want a "light-class" which happens to be a
 struct in D.  I guess there could be a class version as well.

 -- 
 -Anderson: http://badmama.com.au/~anderson/

May 26 2004
parent reply "Walter" <newshound digitalmars.com> writes:
"davepermen" <davepermen hotmail.com> wrote in message
news:c931jl$5hd$1 digitaldaemon.com...
 mixin Addable to get in opAdd, opAddAsign, and such.. mixin Comparable,

 opLess, opLEqual, opEqual, opGEqual, opGreater, opGeek..

Er, for D, that would be opNerd, not opGeek.
Jun 02 2004
parent reply "davepermen" <davepermen hotmail.com> writes:
why not support both? :D

i thought always "damn", none reads my idea.

now big WALTER HIMSELF comes, and replies! i thought YEAH YEAH YEAH, and
then, he talks about the geek/nerd operator..

oh well.. :D

"Walter" <newshound digitalmars.com> schrieb im Newsbeitrag
news:c9lnl6$eei$1 digitaldaemon.com...
 "davepermen" <davepermen hotmail.com> wrote in message
 news:c931jl$5hd$1 digitaldaemon.com...
 mixin Addable to get in opAdd, opAddAsign, and such.. mixin Comparable,

 opLess, opLEqual, opEqual, opGEqual, opGreater, opGeek..

Er, for D, that would be opNerd, not opGeek.

Jun 03 2004
parent reply J Anderson <REMOVEanderson badmama.com.au> writes:
davepermen wrote:

why not support both? :D

i thought always "damn", none reads my idea.

now big WALTER HIMSELF comes, and replies! i thought YEAH YEAH YEAH, and
then, he talks about the geek/nerd operator..

oh well.. :D
  

-- -Anderson: http://badmama.com.au/~anderson/
Jun 05 2004
parent "davepermen" <davepermen hotmail.com> writes:
hm?

"J Anderson" <REMOVEanderson badmama.com.au> schrieb im Newsbeitrag
news:c9uc69$10ct$1 digitaldaemon.com...
 davepermen wrote:

why not support both? :D

i thought always "damn", none reads my idea.

now big WALTER HIMSELF comes, and replies! i thought YEAH YEAH YEAH, and
then, he talks about the geek/nerd operator..

oh well.. :D

-- -Anderson: http://badmama.com.au/~anderson/

Jun 06 2004