Инициализация полей класса

Automatically generated description.

Два дня убил на выявление одной подлой ошибки. Проблема была в том, что на одном компьютере программа работала исправно, а на другом – segmentation fault.

Ошибка возникала по вине неинициализированной переменной (которая представляла собой файловый дескриптор).


А не проявлялась она на одном из компьютеров, по-видимому, из-за различий версий компилятора С++.


Проблема демонстрируется следующим кодом:
class MyClass {
        int myField;
public:
        MyClass(){}
        ~MyClass(){}
        int getMyField(){return myField;}
};
Создадим два объекта этого класса, один – в куче, другой – в стеке, и выведем поля:
#include <iostream>
int main(){
        MyClass *obj = new MyClass();
        std::cout << obj->getMyField() << std::endl;
        MyClass obj2;
        std::cout << obj2.getMyField() << std::endl;
}
Теперь скомпилируем программу в различных версиях компилятора и посмотрим на результаты её выполнения.
$ g++-4.3 main.cpp -o 4.3 && g++-4.4 main.cpp -o 4.4
$ ./4.3 && ./4.4
0
-1217331212
0
134514832
В первом случае результаты одинаковы &#8211; поле успешно инициализировано. Второй же случай более интересен. Мы видим, что новая версия компилятора инициализирует переменную положительной константой (вы можете убедиться в этом, несколько раз запуская программу), тогда как в результате компиляции версией 4.3 получаем меняющееся от запуска к запуску значение в неинициализированном поле класса.


<h2>Вывод</h2>

Если вы планируете создавать объекты в стеке &#8211; инициализируйте все поля класса. Инициализируйте их в любом случае, так, на всякий случай.


<h2>To read</h2>

<ul>
	- [C++ <span class="caps">FAQ</span>. Constructors](http://www.parashift.com/c%2B%2B-faq-lite/ctors.html)
</ul>

<h2>P.S.</h2>

Насколько я знаю, Java и C# не допускает неинициализированных полей.