Yes there are, a couple of ways:
1) Generic approach:
class ServiceBase<T> where T : InstanceBase, new()
{
public InstanceBase GetObject() //you can make the return type even 'T'
{
var v = new T();
v.Method();
return v;
}
}
class ServiceA : ServiceBase<InstanceA>
{
}
class ServiceB : ServiceBase<InstanceB>
{
}
This is just better since it has the least code duplication, but I'm not sure if the genericity is going to be a hassle ever.
2) If that doesn't fit, you can ask the base class to provide their own InstanceBase
. This looks cleaner and simpler. Like:
abstract class ServiceBase
{
public abstract InstanceBase Instance { get; }
public InstanceBase GetObject() //you can make the return type even 'T'
{
Instance.Method();
return Instance;
}
}
class ServiceA : ServiceBase
{
public override InstanceBase Instance { get; } //return new InstanceA() here
}
class ServiceB : ServiceBase
{
public override InstanceBase Instance { get; } //return new InstanceB() here
}
Now from the overridden property Instance
, return an new instance of InstanceBase
or an already instantiated instance. That depends on your logic, but from the shown method it seems, you got to return a new instance every time.
Which suits you depends on your context. Whatever it is, think about:
1) This approach is bad.
public virtual InstanceBase GetObject<T>()
{
var v= (InstanceBase)Activator.CreateInstance(typeof(T), new object[] { });
v.Method();
return v;
}
For one, you have to specify the type argument whenever you're calling the function, two, there is every possibility that one can mess things up.
ServiceA a = new ServiceA();
a.GetObject<InstanceB>(); // not probably what you want.
2) In any case, you can give a new()
constraint for a generic type argument T
if you're going for it.
3) You need not specify empty parameter collection if you're to instantiate with the default constructor. This would do:
var v= (InstanceBase)Activator.CreateInstance(typeof(T));
// or just new T();
4) You seem to not have used any instance members at all in your GetObject
method. If that is the case, then you can have a static method. Whether this should be static or non-static again depends, depending on the call you would want to make. Just have static
in mind.
public static InstanceBase GetObject() //you can make the return type even 'T'
{
var v = new T();
v.Method();
return v;
}
//can call like this too:
ServiceA.GetObject(); //etc