我怎样才能从string表示获得genericstypes?

我有MyClass<T>

然后我有这个string s = "MyClass<AnotherClass>"; 。 我怎样才能从strings获取Type?

一种方法(丑陋的)是parsing出“<”和“>”,并做:

 Type acType = Type.GetType("AnotherClass"); Type whatIwant = typeof (MyClass<>).MakeGenericType(acType); 

但有没有一个更清晰的方式来获得最终的types没有任何parsing等?

generics的格式是名称,字符,types参数的数量,后面跟着逗号分隔的括号中的types列表:

 Type.GetType("System.Collections.Generic.IEnumerable`1[System.String]"); 

我不确定是否有一种简单的方法可以将generics的C#语法转换为CLR想要的stringtypes。 我开始写一个快速的正则expression式来parsing它,就像你在问题中提到的那样,但是意识到除非你放弃了嵌套generics作为types参数的能力,否则parsing将变得非常复杂。

查看Activator.CreateInstance – 你可以用一个types来调用它

 Activator.CreateInstance(typeof(MyType)) 

或者将一个程序集和types名称作为string

 Activator.CreateInstance("myAssembly", "myType") 

这会给你一个你需要的types的实例。

如果您需要Type而不是实例,请使用Type.GetType()方法和您感兴趣的types的完全限定名称,例如:

 string s = "System.Text.StringBuilder"; Type myClassType = Type.GetType(s); 

这会给你的Type的问题。

我需要这样的东西,我写了一些代码来parsing我需要的简单types名称。 当然,还有改进的余地,因为它不会识别像List<string>这样的genericstypes名称,但是它对stringint[]decimal? 等等。 如果这有助于任何人共享。

 public static class TypeExtensions { public static Type GetTypeFromSimpleName(string typeName) { if (typeName == null) throw new ArgumentNullException("typeName"); bool isArray = false, isNullable = false; if (typeName.IndexOf("[]") != -1) { isArray = true; typeName = typeName.Remove(typeName.IndexOf("[]"), 2); } if (typeName.IndexOf("?") != -1) { isNullable = true; typeName = typeName.Remove(typeName.IndexOf("?"), 1); } typeName = typeName.ToLower(); string parsedTypeName = null; switch (typeName) { case "bool": case "boolean": parsedTypeName = "System.Boolean"; break; case "byte": parsedTypeName = "System.Byte"; break; case "char": parsedTypeName = "System.Char"; break; case "datetime": parsedTypeName = "System.DateTime"; break; case "datetimeoffset": parsedTypeName = "System.DateTimeOffset"; break; case "decimal": parsedTypeName = "System.Decimal"; break; case "double": parsedTypeName = "System.Double"; break; case "float": parsedTypeName = "System.Single"; break; case "int16": case "short": parsedTypeName = "System.Int16"; break; case "int32": case "int": parsedTypeName = "System.Int32"; break; case "int64": case "long": parsedTypeName = "System.Int64"; break; case "object": parsedTypeName = "System.Object"; break; case "sbyte": parsedTypeName = "System.SByte"; break; case "string": parsedTypeName = "System.String"; break; case "timespan": parsedTypeName = "System.TimeSpan"; break; case "uint16": case "ushort": parsedTypeName = "System.UInt16"; break; case "uint32": case "uint": parsedTypeName = "System.UInt32"; break; case "uint64": case "ulong": parsedTypeName = "System.UInt64"; break; } if (parsedTypeName != null) { if (isArray) parsedTypeName = parsedTypeName + "[]"; if (isNullable) parsedTypeName = String.Concat("System.Nullable`1[", parsedTypeName, "]"); } else parsedTypeName = typeName; // Expected to throw an exception in case the type has not been recognized. return Type.GetType(parsedTypeName); } } 

使用它就像写这个一样简单:

 Type t; t = TypeExtensions.GetTypeFromSimpleName("string"); t = TypeExtensions.GetTypeFromSimpleName("int[]"); t = TypeExtensions.GetTypeFromSimpleName("decimal?"); 

要从string中获取types对象,请使用:

 Type mytype = Type.GetType(typeName); 

然后你可以传递给Activator.CreateInstance()

 Activator.CreateInstance(mytype); 

我没有太多的时间来parsing这个问题,不过我想我已经看到了类似的答案。 特别是,我认为他们正在做你想做的事情:

entity framework通用存储库错误

 (String.Format("[{0}]", baseType.Name.ToString())).OfType<T>(); 

希望这有帮助,让我知道更具体的,如果这不是。