static data member in class

When I have define getInstance() function inside class I am not getting any error for the static data member static single* ptr.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
class single
{
  private:
	static single* ptr;
	single()
	{}
	public:
	 static single* getInstance()
	 {			
	    if(ptr == NULL)
	    {
		ptr = new single();
	    }
	    return ptr;
	 }
};

But When I define getInstance() function outside of class, I am getting below error for static single* ptr at compiling.
unresolved external symbol "private: static class single * single::ptr"
And it resolved when I initialize the static data member ptr outside of class.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
class single
{
  private:
	static single* ptr;
	single()
	{}
	public:
        static single* getInstance();
};

 single* single::ptr;

 single* single::getInstance()
 {			
    if(ptr == NULL)
    {
	ptr = new single();
    }
    return ptr;
 }
Yes, static data members have to be defined outside the class, as well as declared inside the class.
That's a linker error. You have to initialize static data members outside of the class. In C++17, though, you can make them inline and initialize them in the class body itself.

Also, a better way of doing what you want instead of dealing with dynamic memory and returning pointers is like so:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
class single
{
  private:
	single()
	{}
	public:
        static single& getInstance();
};

 single& single::getInstance()
 {			
        static single s{};
        return s;
 }
Last edited on
I expect it's the other way around. You're missing the declaration of ptr in the first example, but ok in the second?
Thanks All.
In first example it declared but not define.
So for static data member we need to define as well as its a class data member and not specific to any object.

static members are special members whose memory is automatically allocated at compile time and it's scope is entire program but only visible in function which is defined.

static members doesn't require an object to access it. it can call directly using class name.

now answer for your question , objects require separate memory.

for example a class of student, aruns object and vishak object is different, because they have different characteristics. so they have separate memory for each object.

But in the case of static members the only one memory location is available. and it is allocated in compile time. that's why external declaration is given to that.

static members are actually not a part of instance of class, object. It is a part of class or program that's why it need external declaration.
static members are special members whose memory is automatically allocated at compile time and it's scope is entire program but only visible in function which is defined.
No, this is incorrect. Static class members can be accessed by multiple functions and can be private, protected, or public, which have the same meaning as for non-static members.

But in the case of static members the only one memory location is available. and it is allocated in compile time. that's why external declaration is given to that.

static members are actually not a part of instance of class, object. It is a part of class or program that's why it need external declaration.
No, that's not why a separate definition is needed. In fact, there's no reason to require it. Other languages have classes and static data members with the same semantics as in C++ and don't require static data members to be defined like this.
Thanks helios.
Agreed that static data member can be accessed by multiple functions.
And can be private/protected/public like other data member of class.

"No, that's not why a separate definition is needed. In fact, there's no reason to require it. Other languages have classes and static data members with the same semantics as in C++ and don't require static data members to be defined like this. "

Then when static data member get memory???
As we normal data member get memory when instance created.

So, To get memory to the static memory need to define the same! And That's why we need to define static data member again outside of class in .cpp file.
Then when static data member get memory???
As we normal data member get memory when instance created.

So, To get memory to the static memory need to define the same! And That's why we need to define static data member again outside of class in .cpp file.
The memory for static data members is indeed allocated at compile-time (well, more accurately during process initialization), but this is not why the separate definition is required. It's required because the language designer decided to require it. There's no real reason why you can't define static data members like this:
1
2
3
class Foo{
    static std::string bar = "why isn't this valid?";
};
The compiler should be perfectly capable of generating correct initialization code out of such a declaration. The only reason it doesn't is because the language has specified that static data members be defined in a different manner.
Last edited on
if no one said it, you can also access them without an object.
classname::variable is sufficient, you don't need
classname x;
x.variable;
like you would for a non static member variable that was public.
This allows you to make global variables that are marginally safer. You can still screw it up, of course -- some of the problems of globals can't be fixed at all, of course.
I kind of have a love-hate with statics... they are great at times, but today's multicore cpus and the resulting 'thread everything important' designs make them annoying and prone to more scrutiny than single core - single thread designs required.
Last edited on
You can do this now, you just need the keyword inline to indicate that the variable can be multiply-defined (so that the linker emits a weak symbol for it)
1
2
3
class Foo{
    static inline std::string bar = "why isn't this valid?";
};

see https://en.cppreference.com/w/cpp/language/static#Static_data_members
Oh, cool!
Nice, I did not know that worked. That is much cleaner.
C++17, what can't it do. :)
Topic archived. No new replies allowed.