1

是否有一种标准且安全的方法来获取子构造函数初始化列表中的一个基类的地址?

这是我想做的事情:

我有多个类,它们提供一些处理缓冲区的功能(void*,长度),并且我有多个保存数据的类(c 样式结构)。我想用最少的代码向用户提供两者的结合。这是我的想法:

//Parent1 is POD (old c-style structure)
struct Parent1{/*C style stuff*/};

//Parent2 and Parent3 are NOT POD (virtual functions, copy constructors, ...)
class Parent2{public: Parent2(void*, size_t);/*stuff*/};
class Parent3{public: Parent3(void*, size_t);/*stuff*/};

/*order of inhertiance is not guranteed, it could be Parent2, Parent2, Parent3*/
struct Child1 : public Parent1, public Parent2, public Parent3
{
    Child1()
        : Parent2((Parent1*)this, sizeof(Parent1)),
        Parent3((Parent1*)this, sizeof(Parent1))
    {
    }

    //using self() instead of this is trick which I don't prefer to use.
    const Child1* self()const{return this;}
};

这可以很好地编译 gcc,但会在 Visual Studio 上发出警告,稍后我将尝试其他嵌入式编译器。我正在寻找可以通过MISRA C++ 检查多空间检查和任何其他静态分析工具的标准解决方案。

编辑

Visual Studio 警告:警告 C4355: 'this' : used in base member initializer list

4

1 回答 1

0

在 ctor 列表中,通常的转换工作,因此 Derived* 隐式转换为 Base*。没有任何工作。(如果被调用的函数或 ctor 需要这种转换;对于 void* 你会得到一个 reinterpret_cast 等价物)。

但是,您必须意识到生命周期的问题。在构造过程中,该类是半初始化的,因此使用此形式或其任何转换形式可能会导致使用稍后将初始化的部分。这就是你收到警告的原因。对于您的情况,它可能适用也可能不适用。

我通常只允许存储从 传递的指针this,实际使用将在以后进行。

不要使用 c 风格的强制转换来代替 static_cast!而且你的 void* 闻起来很糟糕,考虑采用类型指针并废弃所有强制转换,只留下隐式转换。特别是因为没有发现任何工具可以恢复丢失的类型信息。

于 2013-06-09T12:14:18.580 回答