How to get ref from GetInstance from main app? - c++

I'm following this singleton pattern, why error LNK2001: unresolved external symbol in this case? my problem LOOKs similar, but my issue is not with the definition of the static instance. My problem is is resolving the static GetInstance() definition from another class.
My errors seems different, or previous answers are inadequate. I've tried the suggestions, "You need to define s_instance outside the class" which doesn't make sense to me as a cpp noob. I declare the statics in the header, and define their implementation in the cpp as well.
I also don't need a lecture on thread safety of singletons, handler bindings use signals2...
State.h
class State
{
public:
State(void);
~State(void);
static State* instance;
static State* GetInstance();
...
};
State.cpp
State::AppState mCurrentState;
boost::signals2::signal<void ()> mSignal;
State* instance = NULL;
State* GetInstance()
{
if( instance == NULL)
{
instance = new State();
return instance;
}
else
{
return instance;
}
}
All that compiles fine. Then when I try to access the singleton like this
State *state = State::GetInstance();, I get 'unresolved external symbol' error.
error LNK2019: unresolved external symbol "public: static class State * __cdecl State::GetInstance(void)" (?GetInstance#State##SAPAV1#XZ) referenced in function "public: virtual void __thiscall MesherApp::setup(void)" (?setup#MesherApp##UAEXXZ)
Also tried the following since some say "define outside of class" - what does that even mean?
class State
{
public:
...
}
static State* instance;
static State* GetInstance();
Looking at this question, Static method with a field I don't see how this applies. I am declaring in the .h and defining everything in the cpp file.

Can you simplify?
class State
{
public:
static State& GetInstance()
{
static State _instance;
return _instance;
}
};
See, it's hidden, it's on-demand, it's thread safe and it works without hoop-jumping.
The static initialization ensure the equivalent of instance == NULL there without any additional effort. It also ensures proper destruction at (before) process shutdown (assuming normal termination).
The only assumption this made is that you don't want to be able to 'forcibly' reset the singleton instance.

I think sehe answer is appropriate and if I would ever find my self using singleton I would take that root.
On the other hand the problem with your code is here:
State* instance = NULL;
It should be
State* State::instance = NULL;
I also just noticed another mistake which is:
State* GetInstance()
{
//...
}
should be:
State* State::GetInstance()
{
//...
}

Related

singleton in c++ compile error [duplicate]

This question already has answers here:
Undefined reference to static class member
(9 answers)
Closed 7 years ago.
I tried to make the following singleton class in C++
#pragma once
#include "stdafx.h"
#include <iostream>
class God
{
private:
static God* firstObject;
God()
{
if (firstObject != NULL)
firstObject = this;
}
public:
static God* BuildGod()
{
if (firstObject != NULL)
return firstObject;
else {
God();
return firstObject;
}
}
};
and then use it like so
God* a = God::BuildGod();
Unfortunatley, it won't even compile and it returned the following errors:
LNK2001 unresolved external symbol "private: static class God * God::firstObject" (?firstObject#God##0PAV1#A)
LNK1120 1 unresolved externals
You actually have a worse problem than the build error, because you create a temporary object, and save a pointer to it to be used.
The statement
God();
creates a temporary object, and in the constructor you save a pointer to this temporary object in firstObject which you then return. Using that pointer will then lead to undefined behavior.
One of the usual ways of creating a singleton in C++ would be something like this:
class God
{
public:
static God& get_instance() {
{
static God instance; // This is THE instance
return instance;
}
private:
God() {}
};
A static member of a class has to be defined outside the class, like
class God
{
...
};
God* God::firstObj;
Just beware that having the definition in a header file and including it mamy times calls for trouble.

Forward-declare struct which only has definition in a library cpp

I'm using the bullet 3 physics library, which has the following struct definition inside one of the cpps:
struct btSingleContactCallback : public btBroadphaseAabbCallback
{
btCollisionObject* m_collisionObject;
btCollisionWorld* m_world;
btCollisionWorld::ContactResultCallback& m_resultCallback;
btSingleContactCallback(btCollisionObject* collisionObject, btCollisionWorld* world,btCollisionWorld::ContactResultCallback& resultCallback)
:m_collisionObject(collisionObject),
m_world(world),
m_resultCallback(resultCallback)
{
}
virtual bool process(const btBroadphaseProxy* proxy)
{
btCollisionObject* collisionObject = (btCollisionObject*)proxy->m_clientObject;
if (collisionObject == m_collisionObject)
return true;
//only perform raycast if filterMask matches
if(m_resultCallback.needsCollision(collisionObject->getBroadphaseHandle()))
{
btCollisionObjectWrapper ob0(0,m_collisionObject->getCollisionShape(),m_collisionObject,m_collisionObject->getWorldTransform(),-1,-1);
btCollisionObjectWrapper ob1(0,collisionObject->getCollisionShape(),collisionObject,collisionObject->getWorldTransform(),-1,-1);
btCollisionAlgorithm* algorithm = m_world->getDispatcher()->findAlgorithm(&ob0,&ob1);
if (algorithm)
{
btBridgedManifoldResult contactPointResult(&ob0,&ob1, m_resultCallback);
//discrete collision detection query
algorithm->processCollision(&ob0,&ob1, m_world->getDispatchInfo(),&contactPointResult);
algorithm->~btCollisionAlgorithm();
m_world->getDispatcher()->freeCollisionAlgorithm(algorithm);
}
}
return true;
}
};
The problem is, the struct is never declared in any of the headers, I need to be able to create an object of this type however. The bullet libraries are statically linked, so I figured I should just be able to declare it myself in my main program as such:
struct btSingleContactCallback
: public btBroadphaseAabbCallback
{
btCollisionObject *m_collisionObject;
btCollisionWorld *m_world;
btCollisionWorld::ContactResultCallback &m_resultCallback;
btSingleContactCallback(btCollisionObject *collisionObject,btCollisionWorld *world,btCollisionWorld::ContactResultCallback &resultCallback);
virtual bool process(const btBroadphaseProxy *proxy);
};
This actually works fine, as long as I'm compiling in debug mode. However, when trying to compile in release mode, I'm getting an unresolved symbol error:
physenvironment.obj : error LNK2001: unresolved external symbol "public: __cdecl btSingleContactCallback::btSingleContactCallback(class btCollisionObject *,class btCollisionWorld *,struct btCollisionWorld::ContactResultCallback &)" (??0btSingleContactCallback##QEAA#PEAVbtCollisionObject##PEAVbtCollisionWorld##AEAUContactResultCallback#2##Z)
Could this have anything to do with c++'s name mangling? Is there a way to avoid it, without having to start making modifications in the library itself?
From a five minute look at the library code, you actually should use ContactResultCallback which is public, letting the implementation of btCollisionWorld::contactTest create and use the private btSingleContactCallback for you.
You did not implement the constructor.

Unresolved external symbol when using static

I am new to c++. I started now playing with classes and I am having a noob problem with statics.
class Test
{
public:
Test(){};
~Test(){};
static void test();
static Helper* helper;
};
void Test::test()
{
Object obj = Test::helper->getObject();
//...
}
When I try to compile it gives the error:
main.obj : error LNK2001: unresolved external symbol "public: static class Helper* Test::helper" (?helper#Test##2PAVHelper##A)
What is wrong with my code?
The first answer is correct. The reason behind this is that you need to allocate memory for static objects outside the class definition. If you define the the class in a header file, and include it in several cpp files, the compiler doesn't know where and how you want to create the object that 'helper' points to.
you need to define Test::helper. Write something like this outside the class:
Helper* Test::helper = new Helper;

Public Static Variable access

I'm tring to expose a static variable. I have tried doing this as both just a public static, and using access functions, but when I use the command Stage::SetFramework( this ); in my Framework class, or even if I make systemFramework public and use Stage::systemFramework = this, I get:
framework.obj||error LNK2001: unresolved external symbol "public: static class Framework * Stage::systemFramework" (?systemFramework#Stage##2PAVFramework##A)|
I'm not sure why this isn't working. I'm obviously missing something Can anyone help please?
#pragma once
#include "event.h"
#ifndef Framework
class Framework;
#endif // Framework
class Stage
{
protected:
static Framework* systemFramework;
public:
// static Framework* systemFramework;
// Stage control
virtual void Begin() = 0;
virtual void Pause() = 0;
virtual void Resume() = 0;
virtual void Finish() = 0;
virtual void Event(FwEvent *e) = 0;
virtual void Update() = 0;
virtual void Render() = 0;
static void SetFramework( Framework* FrameworkObject )
{
systemFramework = FrameworkObject;
};
/*
static Framework* GetFramework()
{
return systemFramework;
};
*/
};
Thanks
Listing static class data members in a class only declares them. They must still be defined somewhere. Put this definition into one .cpp file:
Framework *Stage::systemFramework;
That's because you need a FrameWork* Stage::systemFramework; somewhere too (in a .cpp file, typically). This "places" your variable you may, for example for caching reasons, have it next to some othver variables - so the compiler won't just throw it anywhere, so the declaration inside the class definition is just that, a declaration that "there will be one of these variable somewhere". [Or in an embedded system, there may be some part of memory that is backed up by battery power and another part of memory that isn't, and again, where you "place" the variable will matter in this case].
Of course, the public, private or protected inside the class will still determine which parts of the code can access the variable.

C++: static member functions and variables- redefinition of static variable?

I was trying to incorporate the Singleton design pattern into my code, but I started getting a weird error:
main.obj : error LNK2005: "private: static class gameState * gameState::state" (?state#gameState##0PAV1#A) already defined in gameState.obj
If you're not familiar with the singleton pattern, it is basically used to enforce only 1 instance of a certain object in the entire program.
Here is the relevant code:
gameState.h:
class gameState
{
public:
static gameState* Instance() {return state;}
.
.
.
private:
gameState();
static gameState* state;
};
gameState* gameState::state = new gameState();
and right now I'm just using the instance of that object in the main.cpp file:
gameState *currState = gameState::Instance();
.
.
.
for_each(currState->getHumanPieces().begin(),currState->getHumanPieces().end(), drawPieces);
It would seem I am trying to redefine gameState::state, but can't figure out why... help anyone?
that solved that, but one error still remains, which I didn't actually post before as I thought it was just part of the other one:
error LNK2019: unresolved external symbol "private: __thiscall gameState::gameState(void)" (??0gameState##AAE#XZ) referenced in function "void __cdecl `dynamic initializer for 'private: static class gameState * gameState::state''(void)" (??__E?state#gameState##0PAV1#A##YAXXZ)
any good tip on how to fix that one as well?
Thanks both of you, its fixed :D
You need to put the definition of the static gameState* into exactly one source file, i.e. this line:
gameState* gameState::state = new gameState();
If you put it in a header which is included by multiple source files, each has a definition of gameState::state which leads to errors at link-time.
For the follow-up problem, use Vadakkumpadaths advice: you need to provide a definition for gameStates constructor, not only a declaration.
Add definition for your constructor to fix second linker error.
private:
gameState()
{
}
Use a header guard macro for the redefinition problem, and explicitly define your private constructor.