Spec-Zone.ru › C++

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

Задаёт начальные значения статических переменных константой времени компиляции.

Пояснение

Инициализация константой выполняется в следующих случаях:

  • Инициализация ссылки с статической длительностью хранения константным выражением.
  • Инициализация объекта типа POD со статической длительностью хранения константным выражением.
(до C++11)
  • Инициализация ссылки со статической или потоковой длительностью хранения, если выполняются все следующие условия:
  • Каждое полное выражение (включая неявные преобразования), встречающееся в инициализаторе, является константным выражением.
  • Ссылка привязана к одной из следующих сущностей:
    • к lvalue, обозначающему объект со статической длительностью хранения
    • к временному объекту
    • к подобъекту временного объекта
    • к функции
  • Инициализация объекта со статической или потоковой длительностью хранения, если выполняется одно из следующих условий:
    • Если объект инициализируется вызовом конструктора, полное выражение инициализации является константным выражением, однако при этом для объекта и его подобъектов могут также вызываться constexpr-конструкторы (даже если эти объекты имеют типы классов, не являющиеся литеральными).
    • В противном случае объект либо инициализируется значением, либо каждое полное выражение, встречающееся в его инициализаторе, является константным выражением.
(начиная с C++11)
(до C++17)
  • Инициализация переменной или временного объекта со статической или потоковой длительностью хранения инициализатором, полное выражение которого является константным выражением; однако, если инициализируемая сущность является объектом, такой инициализатор может также вызывать constexpr-конструкторы для объекта и его подобъектов (даже если эти объекты имеют типы классов, не являющиеся литеральными).
(начиная с C++17)
(до C++20)
  • Переменная или временный объект(до C++26) со статической или потоковой длительностью хранения инициализируется константой.
(начиная с C++20)

Эффекты инициализации константой совпадают с эффектами соответствующей инициализации, за исключением того, что гарантируется её завершение до начала любой другой инициализации статического или локального для потока(начиная с C++11) объекта.

Примечания

Компилятору разрешается инициализировать другие статические и локальные для потока(начиная с C++11) объекты константой, если он может гарантировать, что значение будет таким же, как при соблюдении стандартного порядка инициализации.

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

Пример

#include <iostream>
#include <array>

struct S
{
    static const int c;
};

const int d = 10 * S::c; // not a constant expression: S::c has no preceding
                         // initializer, this initialization happens after const
const int S::c = 5;      // constant initialization, guaranteed to happen first

int main()
{
    std::cout << "d = " << d << '\n';
    std::array<int, S::c> a1; // OK: S::c is a constant expression
//  std::array<int, d> a2;    // error: d is not a constant expression
}

Вывод:

d = 50

Отчёты об ошибках

Следующие отчёты об ошибках, изменяющие поведение, были применены задним числом к ранее опубликованным стандартам C++.

DR Применяется к Поведение согласно опубликованной версии Корректное поведение
CWG 441 C++98 ссылки нельзя было инициализировать константой такая инициализация стала возможна
CWG 1489 C++11 было неясно, может ли инициализация
объекта значением быть инициализацией константой
может
CWG 1747 C++11 привязка ссылки к функции не могла быть инициализацией константой может
CWG 1834 C++11 привязка ссылки к xvalue не могла быть инициализацией константой может

См. также

  • constinit
  • constexpr
  • конструктор
  • преобразующий конструктор
  • конструктор копирования
  • конструктор по умолчанию
  • explicit
  • инициализация
    • инициализация агрегата
    • копирующая инициализация
    • инициализация по умолчанию
    • прямая инициализация
    • списковая инициализация
    • инициализация ссылки
    • инициализация значением
    • инициализация нулём
  • перемещающий конструктор

© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/cpp/language/constant_initialization

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API