I've got simple singleton class:
class Singleton
{
public:
static Singleton& getInstance()
{
static Singleton instance;
return instance;
}
// private constructor, etc...
}
The question is how should I access class instance from its member functions?
I've seen various code snippets and now I'm curious whether they have any significant differences.
1.
void Singleton::something(){
Singleton &self = getInstance();
self.doSomething();
}
2.
void Singleton::something(){
this->doSomething();
}
3.
void Singleton::something(){
doSomething();
}
is unnecessary complication - in a non-static member function like something we already have an instance, so there is no need to get it separately.
and 3. are the same, only 3. is shorter and more idiomatic - using this-> to access a member in C++ is not common.
I don't think there should be any other member function to get class instance except Singleton::getInstance();, because this is why it exist. Do it as below:
Sungleton &dst=Singleton::getInstance();
In fact, no way to get instance from non-static member function. When there is no class instance , how can you call its non-static member.
Related
In a class I have a static member that represents the singleton instance of that class:
class A {
public:
static const std::shared_ptr<A> INSTANCE;
private:
A();
};
In order to prevent more instances I made the constructor private. Now I have trouble to initialize the static var, because the initializer cannot access a private member. Here's the code I use in the .cpp file:
const std::shared_ptr<A> A::INSTANCE = std::make_shared<A>();
A factory method wouldn't help either, as it would have to be public as well. What else can I do to make this work? Note: I'd like to avoid the typical static get() method if possible.
You can't use make_shared, but you can just create the instance directly:
const std::shared_ptr<A> A::INSTANCE { new A };
The initialization of a static member is unrelated to the constructor, so the global statement is indeed the right way to go. Is it not working for you?
EDIT: I just realized you're trying to avoid using a singleton access method for some reason. Sounds suspiciously like the Borg pattern. :) Unrelated to you r specific question but I'd advise you to reconsider.
I'm browsing some random code and I found some confusing method, the class is a singleton,
class CFoo
{
CFoo* _instance;
CFoo(){};
public:
~CFoo(){};
static CFoo* getInstance()
{
if(!_instance)
_instance = new CFoo;
return _instance;
}
static void deleteInstance()
{
if(_instance)
delete _instance;
}
// just ordinary member method.
void FooMethod()
{
CFoo::getInstance()->BarMethod(); //confusing..
}
// just ordinary member method.
void BarMethod()
{
//code here..
}
};
CFoo* CFoo::_instance = NULL;
Why FooMethod have to call the CFoo::getInstance() to call the BarMethod? Why not just calling BarMethod() directly?
Please advise.
If you call CFoo::getInstance()->BarMethod() within CFoo::FooMethod(), then the this keyword in the BarMethod refers to CFoo::_instance.
If you call BarMethod() within CFoo::FooMethod(), then the this keyword in the BarMethod refers to the same object on which FooMethod() was called.
It is not entirely clear whether there is effectively any difference. On the one hand, the only constructor that you implemented is private and you refer to the class as a Singleton. This supports the fact that only one instance of CFoo should exist, i.e. this == CFoo::_instance should always hold within BarMethod. On the other hand, CFoo has a public copy constructor, so this == CFoo::_instance might not always be true within BarMethod.
You could call the FooMethod and the Barmethod directly if you could create an object of this class. the problem is you can't do it because the construtor is private. the only way you can create the instance is using the getInstance method. and the method ensure it had no more than single object of this class.
That's why it called singleton.
This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
What is so bad about singletons?
Singleton pattern in C++
I want to create a singleton class. For that, I created a class with all its member and methods as static. Something like this.
class a
{
static int a;
static GetA();
}
Now all the classes who want to use my singleton class cannot create any object for my class and also will get same value. I just want to know whether this implementation will solve all the purpose and fulfill all criteria for creating a singleton class.
I prefer:
GlobalObjectMgr& GlobalObjectMgr::instance()
{
static GlobalObjectMgr objMgr;
return objMgr;
}
There is no class member variable required and it is created only when needed.
The conventional Singleton (anti-)pattern isn't a collection of static variables; rather, it is an object with non-static members, of which only one instance can exist.
In C++, this allows you to avoid the biggest problem with static variables: the "initialisation order fiasco". Because the initialisation order is unspecified for static variables in different translation units, there's a danger that the constructor of one might try to access another before it is initialised, giving undefined behaviour. However, it introduces other problems (a similar "destruction order fiasco", and thread safety issues in older compilers), so it's still something to avoid.
If you want a collection of static variables and functions, then put them in a namespace rather than a class:
namespace stuff {
int a;
void do_something();
}
If you think you want a singleton, then think again; you're generally better avoiding globally accessible objects altogether. If you still want one, then you would make a class with a private constructor, and a public accessor that returns a reference to the single instance, along the lines of:
class singleton {
public:
singleton & get() {
static singleton instance;
return instance;
}
int a;
void do_something();
private:
singleton() {}
~singleton() {}
singleton(singleton const &) = delete;
};
I want to know why cant we create object if the constructor is in private section. I know that if i make a method static i can call that method using
<classname> :: <methodname(...)>;
But why can't we create object is what I don't understand.
I also know if my method is not static then also I can call function by the following:
class A
{
A();
public:
void fun1();
void fun2();
void fun3();
};
int main()
{
A *obj =(A*)malloc(sizeof(A));
//Here we can't use new A() because constructor is in private
//but we can use malloc with it, but it will not call the constructor
//and hence it is harmful because object may not be in usable state.
obj->fun1();
obj->fun2();
obj->fun3();
}
So, my question is: why can't we create an object when constructor is private?
Because it is not accessible to the program, that's what private means. If you declared a member function or variable private, you would not be able to access them either. Creating private constructors is actually a useful technique in C++, as it allows you to say that only specific classes can create instances of the type. For example:
class A {
A() {} // private ctor
friend class B;
};
class B {
public:
A * MakeA() {
return new A;
}
};
Only B can create A objects - this is useful when implementing the factory pattern.
A constructor is a special member function. It obeys the same rules as any other method when it comes to accessing it. The private access label prevents class users from invoking/accessing members declared under it.
The "new" operator needs to call the constructor, so if the constructor is private you can not execute the code "obj = new A" except inside member functions of the class A itself.
I would guess that what you have encountered is a technique that is very often used in Java (and yes I know you're writing C++, but the principle is the same) where the designer of the class wants to make sure that one and only one instance of this class will ever exist (which is called a "singleton"). To achieve this, he needs to prevent other code from creating further instances of the class using new, and making the constructor private is one way to do that. Here's a piece of Java code illustrating the technique.
public class MySingleton {
private MySingleton() {
// Private constructor, to prevent instantiation using "new"
// outside of this class.
}
public synchronized static MySingleton getInstance() {
static MySingleton instance = null;
if (instance == null) {
// I can use new here because I'm inside the class.
instance = new MySingleton();
}
return instance;
}
}
Even if you don't know Java, the syntax is similar enough to C++ that you should understand what this code is doing. The point is that the only way to get a reference to an instance of the MySingleton class elsewhere in the code is to call the static class member getInstance().
MySingleton obj = MySingleton.getInstance();
You can't instantiate your class because the constructor is private. private member variables and functions cannot be used outside of the class itself.
If you want to be able to instantiate your class, you have two options.
Option 1 is to make the constructor. This is the Right Thing to do in the vast majority of cases. Making a constructor private is a useful technique, but only when trying to accomplish specific goals.
Option 2 is to create a public static factory method. You would typically do this when Option 1 isn't an option.
class A
{
A();
public:
static A* Create() { return new A; }
void fun1();
void fun2();
void fun3();
};
int main()
{
A *obj = A::Create();
//Here we can't use new A() because constructor is in private
//but we can use malloc with it, but it will not call the constructor
//and hence it is harmful because object may not be in usable state.
obj->fun1();
obj->fun2();
obj->fun3();
}
I have one question about static and non-static function and variable.
1) non-static function access static variable.
It's OK!
class Bar
{
public:
static int i;
void nonStaticFunction() {
Bar::i = 10;
}
};
int Bar::i=0;
2) non-static function access non-static variable
Definitely OK!
3) static function access static variable&funciton
Definitely OK!
4) static function access non-static function
It's OK
class Bar
{
public:
static void staticFunction( const Bar & bar)
{
bar.memberFunction();
}
void memberFunction() const
{
}
}
5) static function access non-static variable
It's OK or not OK? I am puzzled about this!
How about this example
class Bar
{
public:
static void staticFunction( Bar & bar)
{
bar.memberFunction();
}
void memberFunction()
{
i = 0;
}
int i;
};
static function access non-static
variable
It's OK or not OK? I am puzzled about
this!
When called, a static function isn't bound to an instance of the class. Class instances (objects) are going to be the entities that hold the "non-static" variables. Therefore, from the static function, you won't be able to access them without actually being passed or storing elsewhere a specific instance to operate on.
So yes, the code in your last example is valid, because you are passed in an instance. However, you could not do:
static void staticFunction()
{
// error, this function is static, and is therefore
// not bound to a specific instance when called
i = 5;
}
Static means this is independent of a particular instance of the class. Static methods don't have access to the this pointer. That is the reason you need to call them using the class name.
When you call the Static method, you might not even have any instance of the class defined.
non-static means implies an instance, and could be different with different instances.
So, basically, it does not make sense to access non-static members from static methods.
For this, you need to understand what is static.
Static data members exist once for the entire class, as opposed to non-static data members, which exist individually in each instance of a class. They will have a class scope and does not bound to an instance of the class.
To access static member of the class, we use the format as below
::
if you have created 10 objects of a class.
Assume, you were able to access the non-static variable in the static member of the class, When the static function is called, which object's member it needs to change?
It's not ok. Static functions are accessible without having an instance of a class and thus can't access information that you would need an instance to determine.
For example, you don't need a car to know how many wheels it has, blueprints for a general car would suffice (that could be static information) but you can't tell what color the car is unless you're referring to a specific car (that information needs a specific instance of an object.)