alexl <al**********@g mail.comwrites:
I have 2 classes,
class base {
public:
some virtual functions
}
class derived : public base {
public:
derived(base* b);
}
is there a simpler way to turn a base object into derived than the
following
base* b = new base();
b->do some stuff
now he becomes derived
base* d = new derived(b);
There is no simplier way, in C++.
( You are wanting CLOS (Common Lisp Object System), where an object can
( change of class on the run.
(
( (defclass base () ())
( (defmethod do-something ((self base)) (print `(I am a base ,self)))
( (defclass derived (base) ())
( (defmethod do-something ((self derived)) (print `(I am a derived ,self)))
(
( (let ((b (make-instance 'base)))
( (do-something b)
( (change-class b 'derived)
( (do-something b)
( (values))
(
( Which prints:
(
( (I AM A BASE #<BASE #x00033477AFB8> )
( (I AM A DERIVED #<DERIVED #x00033477AFB8> )
(
( Note that's the same object, at the same address.
But in C++, there's no simplier way than to explicitely define a
conversion method that will instanciate a new object. To solve the
identity problem, you have to implement a 'State' design pattern.
http://en.wikipedia.org/wiki/State_pattern
#include <iostream>
using namespace std;
class ChangeableObjec t;
class Base {
protected:
ChangeableObjec t* self;
public:
static Base* factory(Changea bleObject* mySelf){return new Base(mySelf);}
Base(Changeable Object* mySelf):self(my Self){}
virtual void doSomething(voi d){ cout<<"I am a base "<<self<<en dl; }
};
class ChangeableObjec t {
private:
Base* implementation;
public:
typedef Base*(*Factory) (ChangeableObje ct*);
ChangeableObjec t(){ changeClass(Bas e::factory); }
void changeClass(Fac tory factory){ implementation= factory(this); }
void doSomething(voi d){ implementation->doSomething( ); };
};
class Derived:public Base {
public:
static Base* factory(Changea bleObject* mySelf){return new Derived(mySelf) ;}
Derived(Changea bleObject* mySelf):Base(my Self){}
virtual void doSomething(voi d){ cout<<"I am a derived "<<self<<en dl; }
};
int main(void){
ChangeableObjec t* o=new ChangeableObjec t();
o->doSomething( );
o->changeClass(De rived::factory) ;
o->doSomething( );
return(0);
}
/*
-*- mode: compilation; default-directory: "~/src/tests-c++/" -*-
Compilation started at Mon Apr 14 10:11:03
g++ -o state-pattern state-pattern.c++ && ./state-pattern
I am a base 0x603010
I am a derived 0x603010
Compilation finished at Mon Apr 14 10:11:03
*/
--
__Pascal Bourguignon__