我正在编写一个将由很多类实现的接口,我正在编写一个包含这些实现的实例集合的类。每个类都有一个默认的构造函数。
那么,是否有一种简单的方法(例如使用某种反射)将每个实现类的实例放入集合中?除了手动操作外,这很简单,是的,但是很多工作和容易出错(如果我在编写方法时错过了实现怎么办?如果新的实现出现了,我忘了更新给定的方法?)。
所以,我想要的是能够迭代给定命名空间的所有类,或者可能通过所有可用类的列表。然后,我的方法只需通过反射检查给定的类是否实现了给定的接口,如果确实如此,则将其放入集合中。
谢谢。
答案 0 :(得分:2)
您需要调用Assembly.GetTypes()
来获取程序集中的每个类,调用typeof(IMyInterface).IsAssignableFrom
来检查实现该接口的类,然后调用Activator.CreateInstanse
来实例化该类。
使用LINQ:
typeof(IMyInterface).Assembly.GetTypes()
.Where<Type, bool>(typeof(IMyInterface).IsAssignableFrom)
.Select(t => Activator.CreateInstance(typeof(T)))
.ToArray()
答案 1 :(得分:2)
这里没有LinQ,散布开来让你可以看到发生了什么。但除此之外,它与SLaks所写的完全相同。
它是所有实现接口IFoo的类。
List<IFoo> items = new List<IFoo>();
//Iterate through all types
foreach (Type type in Assembly.GetExecutingAssembly.GetTypes) {
//Check the type is public and not abstract
if (!type.IsPublic | type.IsAbstract)
continue;
//Check if it implements the interface IFoo
if (typeof(IFoo).IsAssignableFrom(type)) {
//Create an instance of the class
//If the constructor has arguments put them after "type" like so:
//Activator.CreateInstance(type, arg1, arg2, arg3, etc...)
IFoo foo = (IFoo)Activator.CreateInstance(type);
//Add the instance to your collection
items.Add(foo);
}
}