2012-11-02 68 views
0

我想用一个动态参数创建对象的实例,就像C#私人牛逼的CreateObject <T>()

private Type ClassType { get; set; } 
model = (CreateObject<typeof(this.ClassType)>)ser.Deserialize(sr); 


private T CreateObject<T>() 
{ 
    return (T)Activator.CreateInstance(this.ClassType); 
} 

我想尝试它没有像“startconfig”修复类型。 但它仍然无法正常工作,你能帮助我吗?

 var mi = GetType().GetMethod("CreateObject"); 
     var miConstructed = mi.MakeGenericMethod(this.ClassType); 
     var instance = miConstructed.Invoke(this, null); 
     var model = (instance)ser.Deserialize(sr); 
    } 

    private T CreateObject<T>() 
    { 
     return (T)Activator.CreateInstance(this.ClassType); 
    } 

这并不工作,无论如何,原因:他类型或命名空间名称“类型/命名空间”找不到(是否缺少using指令或程序集引用?)

是happends在铸造ser.Deserialize(SR);

+2

以什么方式不起作用:你会得到一个异常(在这种情况下:什么异常和消息>?)或其他? – Richard

+1

这是什么“ClassType”属性? – logicnp

+0

我得到了编译错误: http://msdn.microsoft.com/en-us/library/hxfhx4sy(v=vs.90).aspx – Ipad

回答

2

你想创建一个T的实例吗?然后:

var model = CreateObject<StartConfig>();  

private T CreateObject<T>() 
{ 
    return (T)Activator.CreateInstance(typeof(T)); 
} 

与你的第二个代码示例,你可能会这样做。

private Type ClassType { get; set; } 
var mi = GetType().GetMethod("CreateObject"); 
var miConstructed = mi.MakeGenericMethod(ClassType); 
var instance = miConstructed.Invoke(this, null); 
model = (instance)ser.Deserialize(sr); 

private T CreateObject<T>() 
{ 
    return (T)Activator.CreateInstance(typeof(T)); 
} 
+0

那么你为什么使用泛型?这就是使用'Activator.CreateInstance'的全部意义......如果您事先知道类型(如果您使用泛型,您必须知道),那么您可以使用ctor。 –

+0

@ user1793913可能会看到编辑...但你应该显示更多的代码,因为它看起来像是,你的架构有一些问题... –

+0

只是为了记录:我的评论是关于OP评论和删除之后。 –

0

的Try ...

public class Factory<T> 
{ 
    public static T getInstance() 
    { 
     return getInstance(typeof(T), null); 
    } 

    public static T getInstance(object[] initializationParameters) 
    { 
     return (T)Activator.CreateInstance(typeof(T), initializationParameters); 
    } 
{ 
0

你要什么你model办?我的意思是界面明智的。您必须定义一个所有类型遵守您反序列化的接口。

public interface IModel 
{ 
    int ComputeFavoriteNumber(); // or a property 
} 

... 

// class is practically unknown to deserializing module 
internal class ErnieModel : IModel 
{ 
    public int ComputeFavoriteNumber() 
    { 
     return 8243721; 
    } 
} 

... 

// deserializing module 
var bf = new BinaryFormatter(); 
using (var ms = new MemoryStream()) 
{ 
    bf.Serialize(ms, new ErnieModel()); // In reality ErnieModel should be unknown to the deserializing code, this is just to fill the Stream with data 
    ms.Position = 0; 
    var model = (IModel)bf.Deserialize(sr); 
    Console.WriteLine("Favorite number: {0}", model.ComputeFavoriteNumber()); 
} 

在这种情况下,您甚至不需要Activator.CreateInstance。但是,如果您只是保存了要创建的类型的完全限定名称或类型本身(不确定是否可行),则确实需要它。

// interfaces/classes the same as above 
Type deserializedType = typeof(ErnieModel); // or get it from wherever, maybe through (Type)bf.Deserialize(stream); ? In reality ErnieModel should be unknown to the deserializing code 
var model = (IModel)Activator.CreateInstance(deserializedType); 
Console.WriteLine("Favorite number: {0}", model.ComputeFavoriteNumber()); 

使用泛型没有意义在此情况下(虽然感觉就像一个好地方,在第一个报名),你必须去与老校友object和铸造到一个已知的接口类型,以实现真正的plugin-像扩展。