0

I have a question related to the initialization of static members in the header files. In the following example:

some_project.h

class MyClass
{
    private:
        void foo() const;
    private:
        static constexpr char array[] = "my array";
        static constexpr const char *ptr = "my pointer";
};

some_project.cpp

constexpr char MyClass::array[];

void MyClass::foo() const
{
    cout << array << ptr << endl;
}

I have to define array[] in cpp file although it is already defined in header file, otherwise I end up with linker undefined reference errors. However this is not happening for the pointer, ptr is working just fine.

I know that C++ allows declarations and initialization inside class declaration in header files if members are const int type. What is the logic behind? Is that because integral data types fits into register and are inlined and therefore no additional definitions in cpp file is needed? Or is it because constexpr works as an C-style macro and is inlined and array is not?

walnut
  • 21,629
  • 4
  • 23
  • 59
Ondrej
  • 817
  • 1
  • 9
  • 16
  • 1
    It's about [*ODR usage*](https://en.cppreference.com/w/cpp/language/definition#ODR-use) of the variables. To print the array you need to take its address (it's ODR-used), but you don't do that for the pointer. – Some programmer dude Dec 06 '19 at 15:07
  • @Ondrej The second half of the second answer explains that it depends on whether the variable is odr-used and what that means. – walnut Dec 06 '19 at 15:20
  • 1
    What version of C++ are you using? In C++17, you don't need the out-of-line definitions. – Brian Bi Dec 06 '19 at 15:52
  • You should read up on the difference between defining and declaring. Then declare in the header and define in a code file. – Yunnosch Dec 06 '19 at 17:07
  • It is cpp14. @Yunnosch, it is not that case. What are you saying is general standard, but cpp allows you to do more - even declaring alongside inicialization in the header without definition - just as that pointer is. If I understand that correctly, if a static constexpr variable is not odr-used, it is not needed to provide definition. – Ondrej Dec 07 '19 at 07:17
  • @Someprogrammerdude, could you kindly clarify why is not pointer ODR-used? Is it because - from the standard - "A variable x whose name appears as a potentially-evaluated expression e is odr-used by e unless x is a reference that is usable in constant expressions..." and pointer is treated as reference? – Ondrej Dec 07 '19 at 08:02
  • 1
    When you use the array, you need to take its address. When you use the pointer, you don't need to take its address, only fetch its value. – Some programmer dude Dec 07 '19 at 10:50

0 Answers0