I was looking into Alexandrescu's singleton created with policies, which is an interesting design. (http://loki-lib.sourceforge.net/html/a00670.html)
However, he first explains that you should guarantee a Singleton's uniqueness, which I agree with. But when you look at the policy implementation, he has a policy CreateWithNew which invokes the new operator on the argument provided with T. which means the constructor has to be public, meaning any user creating the singletonHolder can also instantiate that class directly himself.
Obviously it is still a nice design, but I just wanted to make sure if I missed something important or if he sacrificed the uniqueness for a versatile design.
Thanks!
A test example: The following class has a TestObject which is the Singleton class, and a simple createViaNewPolicy which just uses new to allocate the singleton. notice that the constructor of TestObject has to be public in order for this to work.
//////////////////////////////////////////////////////////////////////////
class TestObject
{
public: // change this to private (to guarantee uniqueness) but then it wont compile
TestObject() {}
int foo() {return 1;}
~TestObject() {}
};
//////////////////////////////////////////////////////////////////////////
template< class T, template <class> class CreationPolicy >
class SingletonHolder
{
public:
T* SingletonHolder<T, CreationPolicy>::Instance()
{
if (!pInstance_)
{
pInstance_ = CreationPolicy<T>::Create();
}
return pInstance_;
}
private:
static T* pInstance_;
};
template< class T, template <class> class CreationPolicy >
T* SingletonHolder<T, CreationPolicy>::pInstance_;
//////////////////////////////////////////////////////////////////////////
template<class T>
class CreateViaNew
{
public:
static T* Create()
{
return new T();
};
};
//////////////////////////////////////////////////////////////////////////
int _tmain(int argc, _TCHAR* argv[])
{
SingletonHolder<TestObject, CreateViaNew> mySingletonHolder;
TestObject* testObj = mySingletonHolder.Instance();
return 0;
}