0

我有一个函数,目前需要一个Type变量。此函数将其粘贴在列表中,并且最终需要将创建该类型的类。

现在我这样做

object o=MyType.GetConstructors()[0].Invoke(new object[0]);

这很老套,并且由于反射(我认为),也不会在中等信任下工作。有没有更好的方法来做到这一点而无需反思?

以这种方式将类型定义为函数的一部分。我需要“懒惰地”创建该类,因为如果不需要它,它可能不会在应用程序中创建。例如,我使用它

AddToList(typeof(Whatever)); 

请注意,我愿意接受有关更改函数调用的建议。我只需要延迟创建对象并将类型(或者创建该类型的对象)存储在列表中。

我考虑过 lambda,但我不确定它们是否可以在这里工作。

4

3 回答 3

3

使用泛型:

public void Method<T>() where T : class, new()
{
  //code
  T t = new T();
}

使用Activator(仍然反射,嗯):

object t = Activator.CreateInstance(yourTypeVariable);

就个人而言,由于是强类型,我更喜欢第一个解决方案。但是,您应该知道这两种方法都只允许无参数构造函数。如果需要传递参数,则需要反射或表达式树。

于 2011-01-14T02:10:23.297 回答
2

另一种替代解决方案是FormatterServices

object instance = FormatterServices.GetUninitializedObject(typeof(MyClass));

请注意,该实例是在没有初始化任何字段/属性的情况下创建的,即使您有

class MyClass
{
   public int i = 99;
   public Object o = new object();
}

instance.i将为 0instance.o并将为空。提供纯粹的非反射解决方案非常困难(因为您总是需要调用o.GetType())。这个方案本质上是序列化对象,然后反序列化成对象,所以不需要使用反射来调用它的构造函数。但是在序列化/反序列化的时候还是有反思的。

于 2011-01-14T02:19:28.730 回答
0

经过对 lambdas 的进一步研究,我发现它们会给我一个更优雅的解决方案,并且它不使用反射

所以我在我的列表定义中使用了

public delegate MyBaseType TypeCreator();

...
public TypeCreator Creator;

在我的函数调用中,一个简单而优雅的 lambda:

AddToList(()=>{return new MyType();});

我认为这比我的反射方法要干净得多,因为它允许将参数放入构造函数中,以及其他一些超出此问题范围的原因。(它和我的项目很相配)

于 2011-01-14T02:37:04.380 回答