2012-02-15 69 views
2

我所试图做的是创建一个基类,用于从它派生的任何内容都会自动与其他类被注册,如:在基类构造函数中使用`this`是否有效?

class System; 
class Object 
{ 
public: 
    Object() 
    { 
     System sys; 
     sys.AddObject(this); 
    } 
    virtual ~Object() 
    { 
     System sys; 
     sys.RemoveObject(this); 
    } 
}; 
class System 
{ 
public: 
    // Some other processing function which operates on all things derived 
    // from Object at one time. 
    void ProcessAllObjectsInExistence(); 

    void AddObject(Object *o) 
    { 
     list.push_back(o); 
    } 
    void RemoveObject(Object *o) 
    { 
     std::vector<Object *>::iterator i = find(list.begin(), list.end(), o); 
     if (*i != list.end()) list.erase(i); 
    } 
private: 
    static std::vector<Object *> list; 
}; 

这是法律和规定?我之所以问这个问题,是因为我从ProcessAllObjectsInExistence()里面读取并写入Object(此处未显示)的数据成员后,发现一些有趣的错误。

即用于单个Object之前我请System.ProcessAllObjectsInExistence()成员是0100,然后内部ProcessAllObjectsInExistence(),第一行是它打印的成员和显示00调试线。痛苦的> <

+1

请问为什么你没有使'AddObject'和'RemoveObject'静态?如果他们只使用静态的'list'变量,那么我认为没有理由他们不可能是静态的。 – 2012-02-15 09:34:35

+0

这是完整的吗? “对象”的构造函数是否会在*将自身添加到列表之后做些什么? @Joachim:它被称为“Borg”模式,至少这就是Alex Martelli在Python中称之为特定版本的模式。 – 2012-02-15 09:40:08

+1

@JoachimPileborg隐藏的静态和'System'的不同实例令人困惑。如果他要走这条路线,那么'系统'应该是一个单身人士,清楚地表明实际上只有一个有效的实例。 (不管是否只有一个实例,因为他这样做是合适的,还有另外一个问题,我们没有足够的信息来判断它) – 2012-02-15 09:57:23

回答

3

在基类内引用this是完全有效的。
但是,在Base类中调用虚拟方法(如果有的话)实际上不会按照您认为的方式工作。

4

是的,在构建基类时访问this是明确定义的。

有一点要注意的是,一个构造函数(或析构函数)期间的*this类型是类目前正在建设中,的类型完全构造的对象将最终拥有。这样做的主要含义是虚拟函数将根据它们在基类中的定义进行调度,并且调用纯虚函数是无效的。

当然,调用AddObject是好的,因为它没有访问正在建设中的对象。我可以看到你的代码出错的唯一方法是,如果你在构造一个对象时从另一个线程调用ProcessAllObjectsInExistence()--这会非常糟糕,因为没有锁来保护对列表的访问。

+0

只要它[有一个实现](http://stackoverflow.com/questions/2089083/),你可以调用一个纯虚函数,对吧? – fredoverflow 2012-02-15 10:48:32

+0

@FredOverflow:只有静态调用它('Base :: fn()')。几乎调用它(只是'fn()')总是未定义的行为。 – 2012-02-15 11:06:09

相关问题