0
votes

I have two classes, Foo and Bar.

Foo.h

class Foo
{
public:
    static void Setm(int i) { m = i; }
private:
    static int m;
};

Bar.h

class Foo;
class Bar
{
 public:
     Bar(int m) {Foo::Setm(m);}
};

main.cpp

#include "Foo.h"
#include "Bar.h"
void main() {
   Bar bar(5);
}

When I compile I get these errors: 1>Foo.obj : error LNK2001: unresolved external symbol "private: static int Foo::m" (?m@Foo@@0HA) 1>Bar.obj : error LNK2001: unresolved external symbol "private: static int Foo::m" (?m@Fool@@0HA)

4

4 Answers

2
votes

A static class member variable for any non integral/enum type must be initialized outside of its declaration/definition.

One such place can be the global scope from main.

i.e. in main.cpp:

 int Foo::m = 0;
0
votes

Put

int FOO::m = 0;

Outside the class definition in a implementation file.

0
votes

you have to initialize static variable:

class Foo
{
public:
    static int m;
static void Setm(int i) { m = i; }
private:
};
int Foo::m=2;

class Foo;
class Bar
{
 public:
 Bar(int m) {Foo::Setm(m);}
};


int main(int argc, char** argv) {
    Foo::Setm(5);
    Bar b(5);
    return 0;
}
0
votes

Couple of things.

  • You should include header guards:

Example:

//Foo.H
#ifndef __FOO_H__
#define __FOO_H__
...
...
#endif

Despite what the other answers state, main is a horrible place to do this. Doing so requires everyone who ever uses this class to have know to do this in their main. How the heck would I know to define static constants in my main when I want to use your header (or even another developer on your team or for another block of code) ? The answer is I wouldn't. It's a lazy practice that will form a bad habit. And don't even get me started on static initialization/destruction fun.

You can't put it in Foo.H because doing so would result in linker errors from the redefinition by every compilation unit that includes your header.

A far better place to do this is in a newly created Foo.[c|.cxx|.cpp|.cc] (whatever suffix you use). Does main work? Yes it works... for you right now. Will it cause issues later? Probably. Is it good form and a solution to be remembered? Absolutely not.

Best Answer:

//Foo.C (NOT MAIN)  
#include<Foo.h>  
int Foo::m = 0;  

What you should also notice is nothing about my answer has anything do with a second class using it in its constructor. Were I to have the points, I would edit the title of your question because it has nothing to do with constructors or class member functions. You are talking about static class methods/functions not member functions/methods.