Topic: Mixins without private inheritance


Author: Xiaolei Yu <dreifachstein@gmail.com>
Date: Sat, 13 Dec 2014 21:52:38 -0800 (PST)
Raw View
------=_Part_1749_1961954173.1418536358349
Content-Type: multipart/alternative;
 boundary="----=_Part_1750_761658613.1418536358356"

------=_Part_1750_761658613.1418536358356
Content-Type: text/plain; charset=UTF-8

I am among those who prefer composition over mixins
through private multiple inheritance. But the thought of another
indirection sometimes make me uncomfortable when a sub-component is used
solely as a value member:

class IStrategy {
protected:
    ~IStrategy() = default;
public:
    virtual void ImplementedByComposition() = 0;
};

class Component {
private:
    IStrategy& mStrategy;
public:
    Component(IStrategy& s);
};

class Composition final : private IStrategy {
private:
    Component mComponent;
private:
    Composition() : mComponent(*this) { }

private:
    void ImplementedByComposition() override;
};

I wish I could write:

class Component {
protected:
    ~Component() = default;
protected:
    virtual void ImplementedByComposition() = 0;
};

class Composition final {
private:
    << Component {
    protected:
        void ImplementedByComposition() override
        {
            /* magic to reference Composition::this */
        }
    }            mValueComponent;

    class << ComponentImpl final : Component {
    protected:
        void ImplementedByComposition() override
        {
            /* magic to reference the implicit Composition::this pointer */
        }
    };

    ::std::unique_ptr<ComponentImpl> mPoinerComponent = { /* like
java-esque this.new ComponentImpl(); */};
};

The use-as-value case should be similar to private inheritance, but with
flexible de/construction order.
The use-as-pointer case is a c++ equivalent of java non-static inner class.


--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_1750_761658613.1418536358356
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">I am among those who prefer composition over mixins throug=
h&nbsp;private&nbsp;multiple inheritance. But the thought of another indire=
ction sometimes make me uncomfortable when a sub-component is used solely a=
s a value member:<div><br></div><div class=3D"prettyprint" style=3D"border:=
 1px solid rgb(187, 187, 187); word-wrap: break-word; background-color: rgb=
(250, 250, 250);"><code class=3D"prettyprint"><div class=3D"subprettyprint"=
><span style=3D"color: #008;" class=3D"styled-by-prettify">class</span><spa=
n style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=
=3D"color: #606;" class=3D"styled-by-prettify">IStrategy</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color=
: #660;" class=3D"styled-by-prettify">{</span><span style=3D"color: #000;" =
class=3D"styled-by-prettify"><br></span><span style=3D"color: #008;" class=
=3D"styled-by-prettify">protected</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">:</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"><br>&nbsp; &nbsp; </span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">~</span><span style=3D"color: #606;" class=3D"style=
d-by-prettify">IStrategy</span><span style=3D"color: #660;" class=3D"styled=
-by-prettify">()</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">=3D=
</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><s=
pan style=3D"color: #008;" class=3D"styled-by-prettify">default</span><span=
 style=3D"color: #660;" class=3D"styled-by-prettify">;</span><span style=3D=
"color: #000;" class=3D"styled-by-prettify"><br></span><span style=3D"color=
: #008;" class=3D"styled-by-prettify">public</span><span style=3D"color: #6=
60;" class=3D"styled-by-prettify">:</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"><br>&nbsp; &nbsp; </span><span style=3D"color: #00=
8;" class=3D"styled-by-prettify">virtual</span><span style=3D"color: #000;"=
 class=3D"styled-by-prettify"> </span><span style=3D"color: #008;" class=3D=
"styled-by-prettify">void</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"> </span><span style=3D"color: rgb(102, 0, 102);"><span style=
=3D"color: #606;" class=3D"styled-by-prettify">ImplementedByComposition</sp=
an></span><span style=3D"color: #660;" class=3D"styled-by-prettify">()</spa=
n><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify">=3D</span><span style=3D=
"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #=
066;" class=3D"styled-by-prettify">0</span><span style=3D"color: #660;" cla=
ss=3D"styled-by-prettify">;</span><span style=3D"color: #000;" class=3D"sty=
led-by-prettify"><br></span><span style=3D"color: #660;" class=3D"styled-by=
-prettify">};</span><span style=3D"color: #000;" class=3D"styled-by-prettif=
y"><br><br></span><span style=3D"color: #008;" class=3D"styled-by-prettify"=
>class</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </s=
pan><span style=3D"color: #606;" class=3D"styled-by-prettify">Component</sp=
an><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span =
style=3D"color: #660;" class=3D"styled-by-prettify">{</span><span style=3D"=
color: #000;" class=3D"styled-by-prettify"><br></span><span style=3D"color:=
 #008;" class=3D"styled-by-prettify">private</span><span style=3D"color: #6=
60;" class=3D"styled-by-prettify">:</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"><br>&nbsp; &nbsp; </span><span style=3D"color: #60=
6;" class=3D"styled-by-prettify">IStrategy</span><span style=3D"color: #660=
;" class=3D"styled-by-prettify">&amp;</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify"> mStrategy</span><span style=3D"color: #660;" cl=
ass=3D"styled-by-prettify">;</span><span style=3D"color: #000;" class=3D"st=
yled-by-prettify"><br></span><span style=3D"color: #008;" class=3D"styled-b=
y-prettify">public</span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">:</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><=
br>&nbsp; &nbsp; </span><span style=3D"color: #606;" class=3D"styled-by-pre=
ttify">Component</span><span style=3D"color: #660;" class=3D"styled-by-pret=
tify">(</span><span style=3D"color: #606;" class=3D"styled-by-prettify">ISt=
rategy</span><span style=3D"color: #660;" class=3D"styled-by-prettify">&amp=
;</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> s</span>=
<span style=3D"color: #660;" class=3D"styled-by-prettify">);</span><span st=
yle=3D"color: #000;" class=3D"styled-by-prettify"><br></span><span style=3D=
"color: #660;" class=3D"styled-by-prettify">};</span><span style=3D"color: =
#000;" class=3D"styled-by-prettify"><br><br></span><span style=3D"color: #0=
08;" class=3D"styled-by-prettify">class</span><span style=3D"color: #000;" =
class=3D"styled-by-prettify"> </span><span style=3D"color: #606;" class=3D"=
styled-by-prettify">Composition</span><span style=3D"color: #000;" class=3D=
"styled-by-prettify"> </span><span style=3D"color: #008;" class=3D"styled-b=
y-prettify">final</span><span style=3D"color: #000;" class=3D"styled-by-pre=
ttify"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">:<=
/span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><sp=
an style=3D"color: #008;" class=3D"styled-by-prettify">private</span><span =
style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"=
color: #606;" class=3D"styled-by-prettify">IStrategy</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #66=
0;" class=3D"styled-by-prettify">{</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"><br></span><span style=3D"color: #008;" class=3D"st=
yled-by-prettify">private</span><span style=3D"color: #660;" class=3D"style=
d-by-prettify">:</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify"><br>&nbsp; &nbsp; </span><span style=3D"color: #606;" class=3D"styled=
-by-prettify">Component</span><span style=3D"color: #000;" class=3D"styled-=
by-prettify"> mComponent</span><span style=3D"color: #660;" class=3D"styled=
-by-prettify">;</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify"><br></span><span style=3D"color: #008;" class=3D"styled-by-prettify">p=
rivate</span><span style=3D"color: #660;" class=3D"styled-by-prettify">:</s=
pan><span style=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp; &n=
bsp; </span><span style=3D"color: #606;" class=3D"styled-by-prettify">Compo=
sition</span><span style=3D"color: #660;" class=3D"styled-by-prettify">()</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><spa=
n style=3D"color: #660;" class=3D"styled-by-prettify">:</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> mComponent</span><span styl=
e=3D"color: #660;" class=3D"styled-by-prettify">(*</span><span style=3D"col=
or: #008;" class=3D"styled-by-prettify">this</span><span style=3D"color: #6=
60;" class=3D"styled-by-prettify">)</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"> </span><span style=3D"color: #660;" class=3D"styl=
ed-by-prettify">{</span><span style=3D"color: #000;" class=3D"styled-by-pre=
ttify"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">}<=
/span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br><br></s=
pan><font color=3D"#000000"><span style=3D"color: #008;" class=3D"styled-by=
-prettify">private</span></font><span style=3D"color: #660;" class=3D"style=
d-by-prettify">:</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify"><br>&nbsp; &nbsp; </span><span style=3D"color: #008;" class=3D"styled=
-by-prettify">void</span><span style=3D"color: #000;" class=3D"styled-by-pr=
ettify"> </span><span style=3D"color: rgb(102, 0, 102);"><span style=3D"col=
or: #606;" class=3D"styled-by-prettify">ImplementedByComposition</span></sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify">()</span><span=
 style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D=
"color: #008;" class=3D"styled-by-prettify">override</span><span style=3D"c=
olor: #660;" class=3D"styled-by-prettify">;</span><span style=3D"color: #00=
0;" class=3D"styled-by-prettify"><br></span><span style=3D"color: #660;" cl=
ass=3D"styled-by-prettify">};</span><span style=3D"color: #000;" class=3D"s=
tyled-by-prettify"><br></span></div></code></div><div><br></div><div>I wish=
 I could write:</div><div><br></div><div><div class=3D"prettyprint" style=
=3D"border: 1px solid rgb(187, 187, 187); word-wrap: break-word; background=
-color: rgb(250, 250, 250);"><code class=3D"prettyprint"><div class=3D"subp=
rettyprint"><span style=3D"color: #008;" class=3D"styled-by-prettify">class=
</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><s=
pan style=3D"color: #606;" class=3D"styled-by-prettify">Component</span><sp=
an style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">{</span><span style=3D"color=
: #000;" class=3D"styled-by-prettify"><br></span><span style=3D"color: #008=
;" class=3D"styled-by-prettify">protected</span><span style=3D"color: #660;=
" class=3D"styled-by-prettify">:</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"><br>&nbsp; &nbsp; </span><span style=3D"color: #660=
;" class=3D"styled-by-prettify">~</span><span style=3D"color: #606;" class=
=3D"styled-by-prettify">Component</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">()</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"> </span><span style=3D"color: #660;" class=3D"styled-by-pre=
ttify">=3D</span><span style=3D"color: #000;" class=3D"styled-by-prettify">=
 </span><span style=3D"color: #008;" class=3D"styled-by-prettify">default</=
span><span style=3D"color: #660;" class=3D"styled-by-prettify">;</span><spa=
n style=3D"color: #000;" class=3D"styled-by-prettify"><br></span><span styl=
e=3D"color: #008;" class=3D"styled-by-prettify">protected</span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">:</span><span style=3D"color=
: #000;" class=3D"styled-by-prettify"><br>&nbsp; &nbsp; </span><span style=
=3D"color: #008;" class=3D"styled-by-prettify">virtual</span><span style=3D=
"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #=
008;" class=3D"styled-by-prettify">void</span><span style=3D"color: #000;" =
class=3D"styled-by-prettify"> </span><span style=3D"color: rgb(102, 0, 102)=
;"><span style=3D"color: #606;" class=3D"styled-by-prettify">ImplementedByC=
omposition</span></span><span style=3D"color: #660;" class=3D"styled-by-pre=
ttify">()</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> =
</span><span style=3D"color: #660;" class=3D"styled-by-prettify">=3D</span>=
<span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span sty=
le=3D"color: #066;" class=3D"styled-by-prettify">0</span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify">;</span><span style=3D"color: #000;=
" class=3D"styled-by-prettify"><br></span><span style=3D"color: #660;" clas=
s=3D"styled-by-prettify">};</span><span style=3D"color: #000;" class=3D"sty=
led-by-prettify"><br><br></span><span style=3D"color: #008;" class=3D"style=
d-by-prettify">class</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify"> </span><span style=3D"color: #606;" class=3D"styled-by-prettify"=
>Composition</span><span style=3D"color: #000;" class=3D"styled-by-prettify=
"> </span><span style=3D"color: #008;" class=3D"styled-by-prettify">final</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><spa=
n style=3D"color: #660;" class=3D"styled-by-prettify">{</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br></span><span style=3D"co=
lor: #008;" class=3D"styled-by-prettify">private</span><span style=3D"color=
: #660;" class=3D"styled-by-prettify">:</span><span style=3D"color: #000;" =
class=3D"styled-by-prettify"><br>&nbsp; &nbsp; </span><span style=3D"color:=
 #660;" class=3D"styled-by-prettify">&lt;&lt;</span><span style=3D"color: #=
000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #606;" cla=
ss=3D"styled-by-prettify">Component</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"> </span><span style=3D"color: #660;" class=3D"styl=
ed-by-prettify">{</span><span style=3D"color: #000;" class=3D"styled-by-pre=
ttify"><br>&nbsp; &nbsp; </span><span style=3D"color: #008;" class=3D"style=
d-by-prettify">protected</span><span style=3D"color: #660;" class=3D"styled=
-by-prettify">:</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify"><br>&nbsp; &nbsp; &nbsp; &nbsp; </span><span style=3D"color: #008;" cl=
ass=3D"styled-by-prettify">void</span><span style=3D"color: #000;" class=3D=
"styled-by-prettify"> </span><font color=3D"#660066"><span style=3D"color: =
#606;" class=3D"styled-by-prettify">ImplementedByComposition</span></font><=
span style=3D"color: #660;" class=3D"styled-by-prettify">()</span><span sty=
le=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"col=
or: #008;" class=3D"styled-by-prettify">override</span><span style=3D"color=
: #000;" class=3D"styled-by-prettify"><br>&nbsp; &nbsp; &nbsp; &nbsp; </spa=
n><span style=3D"color: #660;" class=3D"styled-by-prettify">{</span><span s=
tyle=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp; &nbsp; &nbsp;=
 &nbsp; &nbsp; &nbsp; </span><span style=3D"color: #800;" class=3D"styled-b=
y-prettify">/* magic to reference Composition::this */</span><span style=3D=
"color: #000;" class=3D"styled-by-prettify"><br>&nbsp; &nbsp; &nbsp; &nbsp;=
 </span><span style=3D"color: #660;" class=3D"styled-by-prettify">}</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp; &nbsp; =
</span><span style=3D"color: #660;" class=3D"styled-by-prettify">}</span><s=
pan style=3D"color: #000;" class=3D"styled-by-prettify"> &nbsp; &nbsp; &nbs=
p; &nbsp; &nbsp; &nbsp;mValueComponent</span><span style=3D"color: #660;" c=
lass=3D"styled-by-prettify">;</span><span style=3D"color: #000;" class=3D"s=
tyled-by-prettify"><br><br>&nbsp; &nbsp; </span><span style=3D"color: #008;=
" class=3D"styled-by-prettify">class</span><span style=3D"color: #000;" cla=
ss=3D"styled-by-prettify"> </span><span style=3D"color: #660;" class=3D"sty=
led-by-prettify">&lt;&lt;</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"> </span><span style=3D"color: #606;" class=3D"styled-by-pret=
tify">ComponentImpl</span><span style=3D"color: #000;" class=3D"styled-by-p=
rettify"> </span><span style=3D"color: #008;" class=3D"styled-by-prettify">=
final</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify">:</span><span =
style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"=
color: #606;" class=3D"styled-by-prettify">Component</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #66=
0;" class=3D"styled-by-prettify">{</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"><br>&nbsp; &nbsp; </span><span style=3D"color: #008=
;" class=3D"styled-by-prettify">protected</span><span style=3D"color: #660;=
" class=3D"styled-by-prettify">:</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"><br>&nbsp; &nbsp; &nbsp; &nbsp; </span><span style=
=3D"color: #008;" class=3D"styled-by-prettify">void</span><span style=3D"co=
lor: #000;" class=3D"styled-by-prettify"> </span><font color=3D"#660066"><s=
pan style=3D"color: #606;" class=3D"styled-by-prettify">ImplementedByCompos=
ition</span></font><span style=3D"color: #660;" class=3D"styled-by-prettify=
">()</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </spa=
n><span style=3D"color: #008;" class=3D"styled-by-prettify">override</span>=
<span style=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp; &nbsp;=
 &nbsp; &nbsp; </span><span style=3D"color: #660;" class=3D"styled-by-prett=
ify">{</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br>=
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; </span><span style=3D"color: #800=
;" class=3D"styled-by-prettify">/* magic to reference the implicit Composit=
ion::this pointer */</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify"><br>&nbsp; &nbsp; &nbsp; &nbsp; </span><span style=3D"color: #660=
;" class=3D"styled-by-prettify">}</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"><br>&nbsp; &nbsp; </span><span style=3D"color: #660=
;" class=3D"styled-by-prettify">};</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"><br><br>&nbsp; &nbsp; </span><span style=3D"color: =
#660;" class=3D"styled-by-prettify">::</span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify">std</span><span style=3D"color: #660;" class=3D=
"styled-by-prettify">::</span><span style=3D"color: #000;" class=3D"styled-=
by-prettify">unique_ptr</span><span style=3D"color: #660;" class=3D"styled-=
by-prettify">&lt;</span><span style=3D"color: #606;" class=3D"styled-by-pre=
ttify">ComponentImpl</span><span style=3D"color: #660;" class=3D"styled-by-=
prettify">&gt;</span><span style=3D"color: #000;" class=3D"styled-by-pretti=
fy"> mPoinerComponent </span><span style=3D"color: #660;" class=3D"styled-b=
y-prettify">=3D</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">{</s=
pan><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span=
 style=3D"color: #800;" class=3D"styled-by-prettify">/* like java-esque thi=
s.new ComponentImpl();</span><span style=3D"color: #800;" class=3D"styled-b=
y-prettify"> */</span><span style=3D"color: #660;" class=3D"styled-by-prett=
ify">};</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br=
></span><span style=3D"color: #660;" class=3D"styled-by-prettify">};</span>=
</div></code></div><div><br></div>The use-as-value case should be similar t=
o private inheritance, but with flexible de/construction order.</div><div>T=
he use-as-pointer case is a c++ equivalent of java non-static inner class.<=
/div><div><br></div><div><br></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_1750_761658613.1418536358356--
------=_Part_1749_1961954173.1418536358349--

.