On 03/06/2014 11:04 AM, Gary Willoughby wrote:
I'm trying to create methods across class hierarchies that can be
chained nicely but i'm running into the problem that 'this' declared in
a parent class only refers to that type. Is there a way i can get the
following code to perform in the way i expect?
import std.stdio;
class Foo
{
public auto foo()
{
return this;
}
}
class Bar : Foo
{
public auto bar()
{
return this;
}
}
void main(string[] args)
{
Bar bar = new Bar().bar().foo();
}
test2.d(21): Error: cannot implicitly convert expression ((new
Bar).bar().foo()) of type test2.Foo to test2.Bar
Failed: 'dmd' '-v' '-o-' 'test2.d' '-I.'
How can i make the above marked 'this' refer to Bar when being called in
a chain? When i call the methods like this each method call seems to
implicitly convert 'this' into that method's containing class' instance,
breaking the code and sometimes hiding child methods.
I had the exact problem in C++ which I have solved with the help of
boost::shared_ptr, boost::enable_shared_from_this, and by passing down
the most derived pointer type as a template parameter:
template <class MostDerived>
class FooImpl : public FooInterface,
public boost::enable_shared_from_this<MostDerived>
{
// ...
protected:
typedef boost::shared_ptr<MostDerived> MostDerivedPtr;
MostDerivedPtr foo()(); // <-- HERE, the return type is
// the most derived type
};
Let's try something similar for D:
import std.stdio;
interface Foo
{
// ... needed if there is non-specific interface ...
}
class FooImpl(MostDerived) : Foo
{
public MostDerived foo()
{
return cast(MostDerived)this;
}
}
class Bar : FooImpl!Bar
{
public Bar bar()
{
return this;
}
}
void main(string[] args)
{
Bar bar = new Bar().bar().foo();
}
Ali