Problem in Singleton

Discussion in 'C++' started by Bangalore, Oct 4, 2005.

  1. Bangalore

    Bangalore Guest

    Hi all
    I am finding quite difficulty in understanding the behaviour of th
    followin
    program

    Base class is singleton, so it should allow the creation of only on
    object
    Eventhough it is singleton , i tried to create three objects from it
    and I succeeded with only one object with address "0x1003b010

    Problem
    1. I am not understanding the third object behaviour, here the addres
    of variable i is 0x1003b010( and also in constructor of Base), but i
    first and second cases it is different
    I presume that,when i tried to create second and thir
    object, compiler is not created those. I am not understanding why th
    address o
    i and k is changing

    2. In case of Derived class , I haven't call constructor of derive
    explicitly
    But I know allocation of memory for the Derived class member has be
    done
    Cand anybody tell me how , this has been done

    I know code snippet below is some what clumsy, plz bear with that
    Code snippe


    #include<iostream>

    using namespace std;

    class Base
    {
    private
    //static Base *_instance
    int i,k

    protected
    Base(

    cout <<"Calling Base Constructor \n"
    cout <<"The address of i = " << &i << endl
    cout <<"The address of k = " << &k << endl
    cout <<"Construction of Base class over \n"


    public:
    static Base *_instance
    static Base& Instance();
    int Getdata();
    void Putdata();

    };

    Base& Base :: Instance()
    {
    if (_instance == NULL)
    _instance = new Base();
    return *_instance;
    }

    int Base :: Getdata()
    {
    cout <<"The address of i ="<< &
    <<"\t The address of k = "<< &k << endl
    return i;
    }

    void Base :: Putdata()
    {
    cout <<"The address of i ="<< &
    <<"\t The address of k = "<< &k << endl
    i = 10;



    //Static variabl
    Base *Base::_instance = NULL

    class Derived : public Base
    {
    private
    int j;
    int *ptr;
    static Derived *_instance;

    protected
    Derived()
    {
    ptr = new int;
    *ptr=100;
    cout <<"In Constructor "<
    *ptr <<endl;
    }

    public:
    static Derived & Instance();
    int Getdataderv();
    void Putdataderv();
    };

    Derived & Derived::Instance()
    {
    if (_instance == NULL)
    _instance = static_cast < Derived
    >(&(Base :: Instance()));

    return *_instance;
    }

    int Derived :: Getdataderv()
    {
    return j;
    }

    void Derived :: Putdataderv()
    {
    j = 20;
    }

    //Static variabl
    Derived *Derived::_instance = NULL;

    int main()

    cout <<"The value of Base::_instance = " <
    (Base::_instance);
    cout << "The First Object -----------------------\n";
    Base Base_Object= Base::Instance()
    cout <<"The value of Base::_instance = " <
    (Base::_instance);
    Base_Object.Putdata()
    Base_Object.Getdata()
    cout << "The address of Base_Object = " <
    &Base_Object << endl
    cout << "Work with First Object over--------------\n\n"

    cout << "The Second Objec
    -----------------------\n";
    Base Base_Object_2= Base::Instance()
    cout <<"The value of Base::_instance = " <
    (Base::_instance)
    Base_Object_2.Putdata()
    Base_Object_2.Getdata()
    cout << "The address of Base_Object = " <
    &Base_Object_2 << endl
    cout << "Work with Second Objec
    over--------------\n\n";

    cout <<"Third objec
    ------------------------------\n"
    Base::Instance().Putdata();
    cout<<Base::Instance().Getdata()<<endl;


    cout<<&(Base::Instance())<<endl;
    cout <<"Third object over
    --------------------------\n\n";

    cout <<"Derived Object ----------------------------\n";
    Derived::Instance().Putdataderv();

    cout<<Derived::Instance().Getdataderv()<<endl;


    cout<<&(Derived::Instance())<<endl;
    cout <<"Derived Object over
    ------------------------\n\n";
    }


    output:
    The value of Base::_instance = 0x0The First Object
    -----------------------
    Calling Base Constructor
    The address of i = 0x1003b010
    The address of k = 0x1003b014
    Construction of Base class over
    The value of Base::_instance = 0x1003b010The address of i =0x7ffd8b00
    The address of k = 0x7ffd8b04
    The address of i =0x7ffd8b00 The address of k = 0x7ffd8b04
    The address of Base_Object = 0x7ffd8b00
    Work with First Object over--------------

    The Second Object -----------------------
    The value of Base::_instance = 0x1003b010The address of i =0x7ffd8b08
    The address of k = 0x7ffd8b0c
    The address of i =0x7ffd8b08 The address of k = 0x7ffd8b0c
    The address of Base_Object = 0x7ffd8b08
    Work with Second Object over--------------

    Third object ------------------------------
    The address of i =0x1003b010 The address of k = 0x1003b014
    The address of i =0x1003b010 The address of k = 0x1003b014
    10
    0x1003b010
    Third object over --------------------------

    Derived Object ----------------------------
    20
    0x1003b010
    Derived Object over ------------------------



    Thanks,
    Bangalore
    Bangalore, Oct 4, 2005
    #1
    1. Advertising

  2. Bangalore

    Rolf Magnus Guest

    Bangalore wrote:
    > Problem:
    > 1. I am not understanding the third object behaviour, here the address
    > of variable i is 0x1003b010( and also in constructor of Base), but in
    > first and second cases it is different,
    > I presume that,when i tried to create second and third
    > object, compiler is not created those. I am not understanding why the
    > address of i and k is changing.


    Because you have different objects. You forgot to handle the copy
    constructor and assignment operator, which are automatically created by the
    compiler for your program.

    This:

    Base Base_Object= Base::Instance();

    should actually not compile for a correctly implemented singleton class. It
    makes a copy of your singleton instance, which of course should not be
    possible.
    You need to declare, but not define a private copy constructor and
    assignment operator to prevent unintentional copying of your object.
    Rolf Magnus, Oct 4, 2005
    #2
    1. Advertising

  3. Bangalore

    Bangalore Guest

    > Rolf Magnuswrote:
    Bangalore wrote:
    > Problem:
    > 1. I am not understanding the third object behaviour, here the

    address
    > of variable i is 0x1003b010( and also in constructor of Base), but

    in
    > first and second cases it is different,
    > I presume that,when i tried to create second and third
    > object, compiler is not created those. I am not understanding why

    the
    > address of i and k is changing.
    >

    Because you have different objects. You forgot to handle the copy
    constructor and assignment operator, which are automatically created
    by the
    compiler for your program.

    This:

    Base Base_Object= Base::Instance();

    should actually not compile for a correctly implemented singleton
    class. It
    makes a copy of your singleton instance, which of course should not
    be
    possible.
    You need to declare, but not define a private copy constructor and
    assignment operator to prevent unintentional copying of your
    object.[/quote:c75a7d7286]
    Thanks a lot,

    Can anybody explain my second question??
    Bangalore, Oct 4, 2005
    #3
  4. Bangalore

    mlimber Guest

    Bangalore wrote:
    > Hi all,
    > I am finding quite difficulty in understanding the behaviour of the
    > following
    > program.
    >
    > Base class is singleton, so it should allow the creation of only one
    > object.
    > Eventhough it is singleton , i tried to create three objects from it,
    > and I succeeded with only one object with address "0x1003b010"
    >
    > Problem:
    > 1. I am not understanding the third object behaviour, here the address
    > of variable i is 0x1003b010( and also in constructor of Base), but in
    > first and second cases it is different,
    > I presume that,when i tried to create second and third
    > object, compiler is not created those. I am not understanding why the
    > address of
    > i and k is changing.
    >
    > 2. In case of Derived class , I haven't call constructor of derived
    > explicitly.
    > But I know allocation of memory for the Derived class member has bee
    > done.
    > Cand anybody tell me how , this has been done.
    >
    > I know code snippet below is some what clumsy, plz bear with that.
    > Code snippet

    [snip]
    > Derived & Derived::Instance()
    > {
    > if (_instance == NULL)
    > _instance = static_cast < Derived *
    > >(&(Base :: Instance()));

    [snip]

    This is very bad and the answer to your second question. See the FAQ:

    http://www.parashift.com/c -faq-lite/proper-inheritance.html#faq-21.2

    Cheers! --M
    mlimber, Oct 4, 2005
    #4
  5. Bangalore

    mlimber Guest

    mlimber wrote:
    > Bangalore wrote:
    > > Hi all,
    > > I am finding quite difficulty in understanding the behaviour of the
    > > following
    > > program.
    > >
    > > Base class is singleton, so it should allow the creation of only one
    > > object.
    > > Eventhough it is singleton , i tried to create three objects from it,
    > > and I succeeded with only one object with address "0x1003b010"
    > >
    > > Problem:
    > > 1. I am not understanding the third object behaviour, here the address
    > > of variable i is 0x1003b010( and also in constructor of Base), but in
    > > first and second cases it is different,
    > > I presume that,when i tried to create second and third
    > > object, compiler is not created those. I am not understanding why the
    > > address of
    > > i and k is changing.
    > >
    > > 2. In case of Derived class , I haven't call constructor of derived
    > > explicitly.
    > > But I know allocation of memory for the Derived class member has bee
    > > done.
    > > Cand anybody tell me how , this has been done.
    > >
    > > I know code snippet below is some what clumsy, plz bear with that.
    > > Code snippet

    > [snip]
    > > Derived & Derived::Instance()
    > > {
    > > if (_instance == NULL)
    > > _instance = static_cast < Derived *
    > > >(&(Base :: Instance()));

    > [snip]
    >
    > This is very bad and the answer to your second question. See the FAQ:
    >
    > http://www.parashift.com/c -faq-lite/proper-inheritance.html#faq-21.2
    >
    > Cheers! --M


    Wait a minute, that FAQ doesn't apply. Sorry. I didn't read it closely
    enough. The problem is that you are casting from a base class to a
    derived class. Ordinarily that can be accomplished with, not
    static_cast, but dynamic_cast, which can fail, and in this case, the
    dynamic_cast would certainly fail because the object returned from
    Base::Instance is guaranteed not to be an instance of Derived. Consider
    this code:

    Derived *pD = static_cast<Derived*>(&(Base :: Instance()));
    pD->j = 42;

    You've told the compiler that the object pointed to by pD is a Derived
    object, but in fact it is not. What will happen when Derived::j is
    modified? It will write outside of its allocated memory, and undefined
    behavior results.

    Try this FAQ instead:

    http://www.parashift.com/c -faq-lite/coding-standards.html#faq-27.11

    Cheers! --M
    mlimber, Oct 4, 2005
    #5
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Proton Projects - Moin

    Singleton - Whether Cloneable overrides Singleton

    Proton Projects - Moin, Mar 26, 2007, in forum: Java
    Replies:
    4
    Views:
    3,247
    Proton Projects - Moin
    Mar 27, 2007
  2. Wilhelm
    Replies:
    1
    Views:
    164
  3. Trans
    Replies:
    12
    Views:
    276
    Robert Klemme
    Sep 14, 2007
  4. Paul McMahon
    Replies:
    3
    Views:
    206
    David A. Black
    Jun 9, 2008
  5. Charles Oliver Nutter

    Singleton methods without the singleton class

    Charles Oliver Nutter, Mar 15, 2010, in forum: Ruby
    Replies:
    4
    Views:
    202
    Charles Oliver Nutter
    Mar 22, 2010
Loading...

Share This Page