Определение членов статических данных constexpr - PullRequest
0 голосов
/ 01 мая 2018

Итак, я знаю, что в C ++ статические члены могут быть инициализированы внутри класса, если они являются константным литеральным типом, подобным следующему

class test{
public:
        static constexpr int stc = 1;
private:
        int a = 0;
        int b = 0;
        int c = 0;
};

и статическая переменная constexpr stc могут использоваться, когда компилятор может напрямую подставить значение члена, т. Е.

int main () {int array[test::stc];}  

Однако, если используется в контексте, где значение не может быть напрямую подставлено компилятором:

int main() { const int &cs = test::stc; } 

тогда компилятор (clang) выдает ошибку

c++ -std=c++11 -pedantic    t.cpp   -o t
Undefined symbols for architecture x86_64:
  "test::stc", referenced from:
      _main in t-a8ee2a.o
ld: symbol(s) not found for architecture x86_64

, если статический член не определен вне класса, например:

constexpr int test::stc;

Почему это так?

Ответы [ 3 ]

0 голосов
/ 01 мая 2018

В

int main() { const int &cs = test::stc; } 

test::stc используется odr в

int main () {int array[test::stc];}  

это не так.

Следующий пример из стандарта C ++ 11 поддерживает вышеуказанную идею.

struct S { static const int x = 0; };
const int &f(const int &r);  
int n = b ? (1, S::x)    // S​::​x is not odr-used here
          : f(S::x);     // S​::​x is odr-used here, so a definition is required

С практической точки зрения cs будет недействительной ссылкой, если test::stc не имеет адреса. array, с другой стороны, нужно просто значение test::stc, которое можно оценить во время компиляции. array не требуется адрес test::stc, чтобы быть действительным объектом.

Объект, используемый odr, должен быть определен в программе ровно один раз.

0 голосов

C ++ 17 inline переменные

В C ++ 17, если вы также пометите статический член как inline, то я считаю, что вы можете свободно использовать его или использовать несколько определений в единицах компиляции, например ::100100

#include <iostream>

class MyClass {
    public:
        inline static constexpr int i = 42;
};


int main() {
    const int &cs = MyClass::i;
    std::cout << cs << std::endl;
    std::cout << &MyClass::i << std::endl;
}

Дополнительная информация по адресу: Как работают встроенные переменные?

0 голосов
/ 01 мая 2018
static constexpr int stc = 1; // declares the static var

constexpr int test::stc; // defines the static var

для более подробного объяснения проверьте ссылку ниже

http://www.learncpp.com/cpp-tutorial/811-static-member-variables/

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