Когда и как инициализируются статические данные в C ++? - PullRequest
2 голосов
/ 28 октября 2011

Когда инициализируются статические данные?

Я думаю:

Он может быть инициализирован конструктором,

или

, когда объявлен,

или внекласс

class A::member_d = 5; //  member_d is static  

другие?

Кроме того, когда инициализируются статические переменные области действия файла и когда инициализируются статические переменные области действия функции?

Я думаю, что они инициализируются при объявлении.

спасибо

Ответы [ 4 ]

4 голосов
/ 28 октября 2011

Статические члены класса инициализируются в точке определения.Интегральные типы данных Const являются исключением, которое может быть инициализировано в точке объявления.Когда такая инициализация будет выполнена, это несколько сложно (Google для статическая инициализация фиаско ).Согласно стандарту:

Если инициализация откладывается до некоторого момента времени после первого утверждения main, это должно произойти до первого использования odr любой функции или переменной, определенной в том же переводеединица в качестве переменной для инициализации.

2 голосов
/ 28 октября 2011

Статическая инициализация объекта хранения:

Примечание. Статические объекты-члены инициализируются так же, как объекты в области видимости файла.

  • Объекты в области видимости файла инициализируются в точке определения.
    • Вы можете думать, что все они инициализируются до вызова main ().
    • Подробности см. Ниже.
  • Объекты в области действия функции инициализируются при первом прохождении выполнения по определению.
    • т.е. обычно при первом вызове функции.

Объект инициализируется инициализатором в определении. если вы не предоставите инициализатор, то он будет инициализирован нулями.

int x1;        // zero initialized.
int x2 = 5;    // initialized with 5 
A   y1;        // Default initialized:
               // If A has a user defined constructor this is called.
               // If A has a compiler generated constructor then
               // it is value-initialized which means class objects have their
               // default constructor called and POD objects are zero-initialized
A   y2 = A();  // Default constructed.
A   y3(5);     // Constructor called with value 5.

Статические члены в точности совпадают с объектами и областью видимости файла.

class Z
{
    static int x1; // declaration;
    static int x2;
    static A   y1;
    static A   y2;
    static A   y3;
};
// definition

int Z::x1;
int Z::x2 = 5;
A   Z::y1;
A   Z::y2 = A();
A   Z::y3(5);

Теперь порядок их инициализации сложнее определить. Приказ намеренно оставлен неопределенным, чтобы учесть ситуации компилятора и компоновщика, которые комитет не мог предвидеть.

определяется в:

3.6.2 Инициализация нелокальных переменных

Главное отметить:

Нелокальные переменные со статической продолжительностью хранения инициализируются в результате запуска программы.

Таким образом, в большинстве ситуаций все они будут полностью построены до ввода main.

Как отметили другие. Компилятору разрешено задерживать инициализацию.

3.6.2 Пункт 4

Определяется реализацией, выполняется ли динамическая инициализация нелокальной переменной со статической продолжительностью хранения перед первым оператором main.

Это дополнение в основном сделано для поддержки динамической загрузки библиотек во время выполнения (которые могут быть динамически загружены после запуска main). Но это обеспечивает простую гарантию того, что все статические объекты продолжительности хранения в рамках компиляции будут полностью построены до того, как будут использованы какие-либо объекты или функции в этой компиляции.

3.6.2 Пункт 5

Если инициализация откладывается до некоторого момента времени после первого оператора начальной функции потока, это должно произойти до первого использования odr (3.2) любой переменной с продолжительностью хранения потока, определенной в той же единице перевода в качестве переменной для инициализации.

1 голос
/ 28 октября 2011

Глобальные переменные инициализируются при запуске программы до вызова main().Статические объекты, локальные для области, инициализируются при первом прохождении над ними.

Статические члены класса являются просто глобальными переменными, поэтому см. Выше.

Уничтожение глобальных и статических объектов происходит после того, какmain() возвращает.

(Детали реализации этого довольно сложны, так как все деструкторы должны быть поставлены в очередь для выполнения где-то, а для локальной статики должен быть флаг, указывающий, имеет ли объектуже был создан.)

0 голосов
/ 28 октября 2011

Нет, конечно, конструктор не может инициализировать элементы статических данных.Для константных целочисленных или перечислимых типов вы можете инициализироваться в рамках определения класса.Однако, как правило, вы должны инициализировать вне определения класса.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...