如果我收到一个包含类名的字符串,我想将这个字符串转换为一个真正的类型(字符串中的一个),我该如何做到这一点?
我试着
Type.GetType("System.Int32")
例如,它似乎有效。
但是当我尝试使用自己的对象时,它总是返回null…
我不知道什么将在字符串提前,所以它是我的唯一源转换为它的真实类型。
Type.GetType("NameSpace.MyClasse");
任何想法?
如果我收到一个包含类名的字符串,我想将这个字符串转换为一个真正的类型(字符串中的一个),我该如何做到这一点?
我试着
Type.GetType("System.Int32")
例如,它似乎有效。
但是当我尝试使用自己的对象时,它总是返回null…
我不知道什么将在字符串提前,所以它是我的唯一源转换为它的真实类型。
Type.GetType("NameSpace.MyClasse");
任何想法?
如果类型在mscorlib或调用程序集中,则只能使用类型的名称(当然还有它的名称空间)。否则,你也必须包含程序集名称:
Type type = Type.GetType("Namespace.MyClass, MyAssembly");
如果程序集是强命名的,那么也必须包含所有这些信息。有关更多信息,请参阅Type.GetType(string)的文档。
或者,如果你已经引用了程序集(例如通过一个众所周知的类型),你可以使用程序集。方法:
Assembly asm = typeof(SomeKnownType).Assembly;
Type type = asm.GetType(namespaceQualifiedTypeName);
Try:
Type type = Type.GetType(inputString); //target type
object o = Activator.CreateInstance(type); // an instance of target type
YourType your = (YourType)o;
乔恩·斯基特一如既往是对的:)
更新:您可以以各种方式指定包含目标类型的程序集,如Jon所述,或者:
YourType your = (YourType)Activator.CreateInstance("AssemblyName", "NameSpace.MyClass");
如果你真的想通过名称获取类型,你可以使用以下方法:
System.AppDomain.CurrentDomain.GetAssemblies().SelectMany(x => x.GetTypes()).First(x => x.Name == "theassembly");
请注意,关于要加载的类型的信息越多,就可以大大提高性能。
使用以下LoadType方法来使用System。反射加载所有已注册(GAC)和引用的程序集并检查typeName
public Type[] LoadType(string typeName)
{
return LoadType(typeName, true);
}
public Type[] LoadType(string typeName, bool referenced)
{
return LoadType(typeName, referenced, true);
}
private Type[] LoadType(string typeName, bool referenced, bool gac)
{
//check for problematic work
if (string.IsNullOrEmpty(typeName) || !referenced && !gac)
return new Type[] { };
Assembly currentAssembly = Assembly.GetExecutingAssembly();
List<string> assemblyFullnames = new List<string>();
List<Type> types = new List<Type>();
if (referenced)
{ //Check refrenced assemblies
foreach (AssemblyName assemblyName in currentAssembly.GetReferencedAssemblies())
{
//Load method resolve refrenced loaded assembly
Assembly assembly = Assembly.Load(assemblyName.FullName);
//Check if type is exists in assembly
var type = assembly.GetType(typeName, false, true);
if (type != null && !assemblyFullnames.Contains(assembly.FullName))
{
types.Add(type);
assemblyFullnames.Add(assembly.FullName);
}
}
}
if (gac)
{
//GAC files
string gacPath = Environment.GetFolderPath(System.Environment.SpecialFolder.Windows) + "\\assembly";
var files = GetGlobalAssemblyCacheFiles(gacPath);
foreach (string file in files)
{
try
{
//reflection only
Assembly assembly = Assembly.ReflectionOnlyLoadFrom(file);
//Check if type is exists in assembly
var type = assembly.GetType(typeName, false, true);
if (type != null && !assemblyFullnames.Contains(assembly.FullName))
{
types.Add(type);
assemblyFullnames.Add(assembly.FullName);
}
}
catch
{
//your custom handling
}
}
}
return types.ToArray();
}
public static string[] GetGlobalAssemblyCacheFiles(string path)
{
List<string> files = new List<string>();
DirectoryInfo di = new DirectoryInfo(path);
foreach (FileInfo fi in di.GetFiles("*.dll"))
{
files.Add(fi.FullName);
}
foreach (DirectoryInfo diChild in di.GetDirectories())
{
var files2 = GetGlobalAssemblyCacheFiles(diChild.FullName);
files.AddRange(files2);
}
return files.ToArray();
}