Generic abstract singleton with custom constructor in C #
I want to write a generic singleton with an external constructor. In other words, the constructor can be changed. I have two projects, but I don't know if they are practical or not.
-
The first is to ensure that the constructor of the derived class is non-public, but I don't know if there is a way for it?
-
Second, do you need to use a delegate and call it inside the constructor?
It doesn't have to be a constructor. The reason I chose a custom constructor is doing some custom initialization.
Any suggestions would be appreciated :)
a source to share
Ok, here is my solution. I used reflection to test public constructors. Please comment if I am missing something.
public abstract class Singleton<T> where T: class
{
private static volatile T _instance;
private static object _lock = new object();
protected Singleton()
{
ConstructorInfo[] constructorPublic = typeof(T).GetConstructors(BindingFlags.Public | BindingFlags.Instance);
if (constructorPublic.Length > 0)
{
throw new Exception(String.Format("{0} has one or more public constructors so the property cannot be enforced.",
typeof(T).FullName));
}
}
public static T Instance
{
get
{
if (_instance == null)
{
lock (_lock)
{
if (_instance == null)
{
ConstructorInfo constructorNonPublic = null;
try
{
constructorNonPublic = typeof(T).GetConstructor(BindingFlags.Instance | BindingFlags.NonPublic, null,
new Type[0], null);
}
catch (Exception e)
{
throw e;
}
if (constructorNonPublic == null || constructorNonPublic.IsAssembly)
{
throw new Exception(String.Format("A private or protected constructor is missing for {0}",
typeof (T).Name));
}
_instance = constructorNonPublic.Invoke(null) as T;
}
}
}
return _instance;
}
}
}
a source to share
That sounds good. I wonder if configuring this via IoC will be easier and easier to maintain. Most IoC containers will support singleeton style object reuse and highly customizable initialization. No side effect of making your subject look ugly.
Singleton is good, but heavily overhauled. Of course, Iām as much to blame for this as the next geek ...
a source to share
Here is one way to do it, If I could understand you correctly.
public abstract class MySingletonBase<T>
where T : class
{
protected MySingletonBase()
{
}
// All other functions that will be inherited.
}
public class MySingleton<T> : MySingletonBase<T>
where T : class
{
private static MySingleton<T> instance;
protected MySingleton()
{
}
public static MySingleton<T> GetInstance()
{
if (instance == null)
{
instance = new MySingleton<T>();
}
return instance;
}
}
a source to share