C# 在运行时创建泛型类型的新实例,而不进行类型检查

C# 在运行时创建泛型类型的新实例,而不进行类型检查,c#,.net,reflection,interface,solid-principles,C#,.net,Reflection,Interface,Solid Principles,下面的设计只是一个显示我的问题的模板 public interface IHero { string Name { get; } int Level { get; } } public interface IWarlock : IHero { string MagicType { get; } } public interface IKnight : IHero { string CommandHierarchy { get; } } public class

下面的设计只是一个显示我的问题的模板

public interface IHero
{
    string Name { get; }
    int Level { get; }
}
public interface IWarlock : IHero
{
    string MagicType { get; }
}
public interface IKnight : IHero
{
    string CommandHierarchy { get; } 
}
public class Warlock : IWarlock, IHero
{

    string IWarlock.MagicType { get { throw new NotImplementedException(); } }

    string IHero.Name { get { throw new NotImplementedException(); } }

    int IHero.Level { get { throw new NotImplementedException(); } }

    public Warlock(string name, int level, string magicType)
    {

    }
}
public class Knight : IKnight, IHero
{

    string IKnight.CommandHierarchy { get { throw new NotImplementedException(); } }

    string IHero.Name { get { throw new NotImplementedException(); } }

    int IHero.Level { get { throw new NotImplementedException(); } }

    public Knight(string name, int level, string commandHierarchy)
    {

    }
}
public class NullHero : IHero
{

    public string Name { get { return string.Empty } }

    public int Level { get { return -1; } }
}

class Program
{
    static void Main(string[] args)
    {

    }
    //Increments the hero's level.
    static IHero LevelUp(IHero hero)
    {
        if (hero is IWarlock)
            return new Warlock(hero.Name, hero.Level + 1, (hero as IWarlock).MagicType);
        else if (hero is IKnight)
            return new Knight(hero.Name, hero.Level + 1, (hero as IKnight).CommandHierarchy);
        else
            return new NullHero();
    }
}
问题是,下次我添加一个新的英雄时,我必须在LevelUp函数中添加另一个if语句,这会变得很混乱

我知道我可以使用Activator.CreateInstance创建一个新实例,但是有两个问题,1。所有对象都是不可变的。2.构造函数中参数的数量和类型

有谁能提出解决这个问题的办法吗

编辑: 是的,评论部分的每个人都是正确的。我可以在IHero界面中将LevelUp添加为一个定义

public interface IHero
{
    string Name { get; }
    int Level { get; }
    IHero LevelUp();
}

也许我选择了错误的概念来表达我的问题,但假设我想要在模板中所示的外部处理LevelUp。有没有一种方法可以解决我唯一的问题,那就是创建IHero类型的新实例而不必进行类型检查?

由于您的对象是不可变的,并且您希望在每个hero的特定类中保留LevelUp逻辑,因此您最好将LevelUp方法添加到IHero接口中

public interface IHero
{
    string Name { get; }
    int Level { get; }
    IHero LevelUp();
}
在您的特定英雄类中,您可以实现这样的LevelUp方法

public IHero LevelUp()
{
    return new Warlock(this.Name, this.Level + 1, this.MagicType);
}
为了向后兼容,您可以保留静态leveup函数,但是您应该重构它

static IHero LevelUp(IHero hero)
{
    return hero.LevelUp();
}

为什么不在IHero中定义LevelUp?然后,任何实现都会简单地返回
这个
(当然,我会质疑您是否真的需要在那里返回任何东西)。我认为您应该有一个实现IHero的类,并且您的两个英雄都应该继承该类。现在你将在每一个新的副英雄类型中重新定义英雄。但它们都具有相同的属性(名称和级别),iguess将执行相同的操作。另外,你的升级功能似乎很奇怪,因为你给了整个英雄,它会返回一个英雄。在IHero中创建一个类似“LevelUp()”的方法,然后从那里开始执行。@pijemcolu是的,在这种情况下我可以。因为在IHero中将LevelUp作为一个定义是有意义的。但就像我说的,这只是一个简单的模板。我的业务逻辑要复杂得多(我无法透露),但问题是相同的。也许我所要求的是不可行的,但我需要和社区确认一下。一切都是可行的,但也要付出理智的代价。你看过仿制药吗。您的LevelUp将看起来是静态的T LevelUp(T hero),其中T:IHero{…hero.Level++;…}
@pijemcolu您所建议的与我在模板中显示的没有什么不同。我可以简单地完成Level++的工作,但我喜欢保持我的对象不变,因此Level++无法工作。只能通过返回对象的新实例来修改它们。。。这将创建对象的新实例,无论它是什么类型。谢谢,我将对此进行研究。