创建自定义标准流实现时的编译器警告

时间:2011-08-03 19:37:04

标签: c++ stream compiler-warnings

我有一个Visual Studio 2008 C ++应用程序,我在其中创建了自定义streambuf和流实现。我使用Angelika Langer给出的方法来创建下面详述的流:

class MyOutputStream_3 : private MyStreamBuf, public ostream {
public:
    MyOutputStream_3() : ostream((MyStreamBuf*) this), ios(0) {};
    virtual ~MyOutputStream_3() { sync(); }
    // ...
}; 

但是,Visual Studio给了我一个warning

warning C4355: 'this' : used in base member initializer list

代码工作正常,但我担心编译器会告诉我,我所做的事情在某些情况下可能会破坏,或者可能是不可移植的。

这是我在这个例子中可以忽略的东西,或者我应该怎么做来解决我的问题?

3 个答案:

答案 0 :(得分:2)

它警告你在初始化列表中使用this,因为从技术上讲,this尚不存在,因为构造函数还没有完成执行(也没有任何成员对象的构造函数)并将它传递给函数可能会在尝试使用该对象(包含尚未调用其构造函数的对象)时引发问题。

如果您只是存储指针以供以后使用,代码应该可以工作。但是当你回到这段代码并忘记你不应该使用那个指针时,你可能会犯错,而无法解释你的程序崩溃的原因。

以下是该警告的Microsoft页面:http://msdn.microsoft.com/en-us/library/3c594ae3.aspx

答案 1 :(得分:1)

C ++ 03标准在12.6.2 / 7“初始化基础和成员”的注释中有这一点:

  

[注意:因为mem-initializer是在构造函数的范围内计算的,所以this指针可以在mem-initializer的表达式列表中用来引用正在初始化的对象。 ]

我认为发出警告是因为this指针引用的对象未完全初始化,因此存在一些潜在的危险。只要您的基础实际上没有使用对象的未初始化部分,直到它们被初始化之后,您应该没问题。

作为警告的MSDN文档(http://msdn.microsoft.com/en-us/library/3c594ae3.aspx),请提及:

  

实际上,您已将指向未构造对象的指针传递给另一个构造函数。如果其他构造函数访问任何成员或调用成员函数,结果将是未定义的。

答案 2 :(得分:0)

顺便提一下,只有在mem-initializer列表中明确使用this时才会发生这种情况。传递尚未构造的成员变量的地址不会引发C4355。

如果需要证明,请查看fstream的构造函数。

相关问题