Single instance of an object - c++11

I'm trying to implement a singleton-like object with C++11. I got this example from another user.
It creates an object with the constructor and the copy constructor private and default, as well as an instance() function to return static object.
As I understand this should prevent the creation of two instances of this object. But as you can see in my main.cpp, I create two instances and it compiles and runs.
Is my object creation wrong or what? I don't get it.
object.hpp:
#ifndef OBJECT_H
#define OBJECT_H
#include <iostream>
using namespace std;
class Object
{
private:
Object() = default;
Object(const Object&) = delete;
public:
// Singleton in C++11
static Object& instance() { static Object z; return z; }
};
#endif // OBJECT_H
main.cpp:
#include "object.hpp"
int main()
{
Object* object = new Object();
object->instance();
Object* object2 = new Object();
object->instance();
return 0;
}

When I try to compile your code, I get a proper error from the compiler:
main.cpp: error: calling a private constructor of class 'Object'
Object* ob1= new Object() ;
So I would not be able to create two objects using new.

First your code in main won't compile. Object default constructor is private, so you won't be able to do :
Object* object = new Object();
Second, as instance() is static (means not related to any instance) there is no need to call it from an object, the class name suffices :
Object& theInstance = Object::instance();
Finally, the code of instance is :
static Object& instance()
{
static Object z;
return z;
}
It's OK. A static variable in a C++ function means that the object is instanciated once : when the function is ran for the first time. Then z won't be destroyed at the end of the function (contrary to other so-called local variables) and will be re-used for next calls of instance.
So at first call of instance :
z is created
z z is returned
At next calls :
z is returned
A singleton is a class which implies only one instance will be created. You can verify the objects are the same with :
Object& a = Object::instance();
Object& b = Object::instance();
std::cout << &a << std::endl;
std::cout << &b << std::endl;
a and b should have the same memory adress.
This is the expected behaviour of a singleton : if the object construction function (instance) is called several times, the same instance will be returned.
So as you said, instance actually prevents the creation of two Object. Maybe you expected you program to return some error on the second call of instance. If you wan't this behaviour, you'll have to make it yourself using expections or returning NULL. Yet, The code you wrote shows the classic way singletons are done in C++.

Related

C++: convert not from obj1 to obj2, but from obj1* to obj2?

A constructor for MyClass takes a pointer to another such object.
The C++ MyClass is functionally the same as a C "class" based on a typedef'd struct called MyType_T. (The C++ class is basically a wrapper to the old C code.) I'd like to be able to pass in a MyClass* anywhere I could pass in a MyType_T* before.
I'd like to write an automatic conversion of any MyClass* to MyType_T*, but I guess what's throwing me is that my type converter is written to take a MyClass not a MyClass*. Even though I'm sure that's the problem, I can't think of what syntax would solve it. I've thought about making a friend implementation of the cast, but I can't put it before the definition of class MyClass because it won't know the offset of thing. And I can't put after the definition of class MyClass because the MyClass constructor wants to use that conversion.
typedef struct MyStruct {
int iFoo;
struct MyType* ptypeParent;
} MyType_T;
void MyTypeCreator( MyType_T* ptypeSelf, int iFoo_in, MyType_T* ptypeParent );
class MyClass {
public:
MyClass( int iFoo, MyClass* pclassParent ) {
MyTypeCreator( &thing, iFoo, pclassParent ); <--------------- PROBLEM
MyTypeCreator( &thing, iFoo, &pclassParent->thing ); <------- WORKS
};
operator MyType_T*() { return &thing; } <---------------- INCORRECT: attempts to convert MyClass, not MyClass*, to MyType_T*.
MyType_T thing;
};
QUESTION 1: how to write a convertor from MyClass* instead of MyClass?
QUESTION 2: how can such a convertor check for NULL input? (If thing isn't offset of 0, but say 8, then converting from a NULL pclass without a check would give a value of 0x00000008, not NULL...)

Shared_ptr seems to work on copy, not on original object

I got 2 classes that represent Player and I want to keep in one of them pointer to another one.
So inside my view::Player I create pointer to logic::Player
namespace view {
class Player {
std::shared_ptr<logic::Player> m_player;
//logic::Player* m_player;
public:
void create(logic::Player& player) {
m_player = std::make_shared<logic::Player>(player);
//m_player = &player;
}
};
}
view::Player is created in view::GameState and simply initialised like this
m_playerOneView.create(m_game.getActivePlayer());
m_game is logic::Game object
logic::Game has std::vector<logic::Player>, and public method that returns active one
logic::Player& logic::Game::getActivePlayer() {
return m_players[m_activePlayer];
}
And finnaly
namespace logic {
class Player {
std::string m_name;
int position;
};
}
Now I need original object of logic::Player pointed by std::shared_ptr in my view::Player class. I could simply do that by changing that to raw pointer and it works then (2 commented lines do what I want to achieve basicly). But when I try to do this on std::shared_ptr, I seem to work on copy of logic::Player, because when I update his position for example, it changes everywhere in the game but not in view::Player. How to do that using std::shared_ptr then?

Derived class initialization with parameter of another derived class

I am new in Abstract classes so please excuse any ignorant mistakes
The exercise is given from my school, so the main.cpp file is to be used, almost as it is
I am trying to create a simple calculator in Eclipse using C++11
There exists a simple Abstract class with two virtual methods.
The two derived classes are simply the "Result" and the "Const" classes.
This is the header file of the Abstract class called
Expression.h
class Expression
{
public:
Expression();
virtual ~Expression();
//methods
};
Following is the source file of Expression
Expression.cpp
#include "expression.h"
#include <iostream>
Expression::Expression(){}
Expression::~Expression(){}
Then I have created two classes called Const and Result
Const.h
#include <iostream>
#include "expression.h"
class Const : public Expression
{
public:
Const(int value);
//inherited methods
private:
int value;
};
and the source file
Const.cpp
#include "expression.h"
#include "Const.h"
Const::Const(int x)
{
value=x;
};
//inherited methods
Result.h
#include <iostream>
#include "expression.h"
#include "Const.h"
class Result : public Expression
{
public:
Result(Const& c);
//inherited methods
private:
double value;
};
Result.cpp
#include "expression.h"
#include "Result.h"
Result::Result(Const& c)
{
value=c.point;
};
//inherited methods
So what i need is to understand
main.cpp
#include <iostream>
#include "expression.h"
#include "const.h"
#include "result.h"
void testResult()
{
Result res (new Const(4));
//Here an inherited method will be used to print the contents of object res
}
int main()
{
testResult();
return 0;
}
The problem i can't solve is the line
Result res (new Const(4));
The error i get is
Conversion from 'Const* to non-scalar type 'Result' requested
The thing is that what is described in this line should be used as it is, and i can't seem to find exactly what it is.
EDIT
The question as asked firstly was apparently misleading due to my fault, tried to fix the question so as to describe exactly my problem
You started correctly, by creating a common base class for both Const and Result, but then completely ignored it.
All your problems are indeed in this line:
Result res = (new Const(4));
First of all, operator new in C++ returns a pointer, not a reference. Also, this would be a good place to make use of your base class:
Expression* res = new Const(4);
Since you declared methods evaluate() and print() as virtual, the object res is pointing to will be correctly resolved as an instance of Const when you call res->print() or res->evaluate().
This will use Const version of print(). If you want to use the Result version - abstract classes won't help you here, you need to use casting. Create your own operator=(Const &) in Result or operator Result() in Const.
If you had two derived classes DerivedClass1 and DerivedClass2 both derived from some BaseClass then to instantiate a pointer to a DerivedClass1 and use it in polymorphic way use:
BaseClass* p = new DerivedClass1;
To create a base class pointer to a DerivedClass2 use:
BaseClass* p = new DerivedClass2;
And not the:
DerivedClass1* p = new DerivedClass2;
In your example both Result and Const classes are derived from Expression class hence the confusion. To pass in an argument of SomeClass& type, create a temporary object of SomeClass and pass it in:
SomeClass o;
someFunction(o);
One issue is that
double point= value;
doesn't initialize your member, but a new unused local variable.
just do
point = value;
Class Result and Const are two different classes. This means the type conversion
Result *res = (new Const(4));
is not possible. To do what you want, since both classes inherit from Expression, do:
Expression * res = new Result( objConst);
Where objConst is a Const object.

adding a shared_ptr object on a weak_ptr container

My class is based on boost::asio tutorial.
This class has a private ctor, is derived from enable_shared_from_this.
its static member function return a shared_ptr from the object created.
I want to store those pointers on a list of weak_ptr, so the list don't need to worry about its life time, either prolong it.
The caller tcp_serve instantiate tcp_connection with create method:
tcp_server:
tcp_connection::pointer new_connection =
tcp_connection::create(acceptor_.get_io_service());
tcp_connection:
PUBLIC:
typedef boost::shared_ptr<tcp_connection> pointer;
static pointer create(boost::asio::io_service& io_service)
{
return pointer(new tcp_connection(io_service));
}
PRIVATE:
tcp_connection(boost::asio::io_service& io_service)
: _socket(io_service), _timer(io_service)
{
}
I am trying to create a list on the tcp_server, I tried many different kind of types, but I can't rightly added the object to the list:
std::list<std::weak_ptr<tcp_connection>> connections;
connections.push_back(new_connection);

boost bind to a data member callback behavior

Can someone please explain this piece of code?
struct Class {
boost::function<void()> member;
};
Class c;
boost::function<boost::function<void()>()> foo = boost::bind(&Class::member, &c);
boost::function<void()> bar = boost::bind(&Class::member, &c);
Why does the definition of bar compile and what is the result of it?
Edit: foo() works as expected, calling c.member(), but bar() doesn't.
The first call is used to "generate" an extractor functor. That functor, when called, will return the member that it was bound to.
The second call just hides the return type of the functor that is passed in (which is the same as in the first example). So essentially, calling bar will do nothing.
You would need to bind if your class was like that:
class Class {
public:
void member();
};
Then what you want to do is that :
Class c;
boost::function<void()> the_function_i_want_to_call = boost::bind(&Class::member, c);
the_function_i_want_to_call.call();

Resources