¿Hay alguna manera de crear una instancia de una clase basada en el hecho de que sé el nombre de la clase en tiempo de ejecución? Básicamente, tendría el nombre de la clase en una cadena.
¿Hay alguna manera de crear una instancia de una clase basada en el hecho de que sé el nombre de la clase en tiempo de ejecución? Básicamente, tendría el nombre de la clase en una cadena.
Respuestas:
Eche un vistazo al método Activator.CreateInstance .
var driver = (OpenQA.Selenium.IWebDriver)Activator.CreateInstance("WebDriver", "OpenQA.Selenium.Firefox.FirefoxDriver").Unwrap();
Es muy simple. Suponga que su nombre de clase es Car
y el espacio de nombres es Vehicles
, luego pase el parámetro Vehicles.Car
que devuelve el objeto de tipo Car
. De esta manera, puede crear cualquier instancia de cualquier clase de forma dinámica.
public object GetInstance(string strFullyQualifiedName)
{
Type t = Type.GetType(strFullyQualifiedName);
return Activator.CreateInstance(t);
}
Si su nombre completo (es decir, Vehicles.Car
en este caso) está en otro conjunto, Type.GetType
será nulo. En tales casos, usted tiene bucle a través de todos los conjuntos y encontrar el Type
. Para eso puedes usar el siguiente código
public object GetInstance(string strFullyQualifiedName)
{
Type type = Type.GetType(strFullyQualifiedName);
if (type != null)
return Activator.CreateInstance(type);
foreach (var asm in AppDomain.CurrentDomain.GetAssemblies())
{
type = asm.GetType(strFullyQualifiedName);
if (type != null)
return Activator.CreateInstance(type);
}
return null;
}
Ahora, si desea llamar a un constructor parametrizado, haga lo siguiente
Activator.CreateInstance(t,17); // Incase you are calling a constructor of int type
en vez de
Activator.CreateInstance(t);
dynamic
código; consulte stackoverflow.com/a/2690661/904521 )
strFullyQualifiedName
con str
, fullyQualifiedName
hará el trabajo.
str
se usa como parte de la convención de nomenclatura para variables. Ciertas organizaciones y proyectos insisten en seguir esto, por lo tanto, solía. Si hubiera trabajado en ciertas organizaciones / proyectos, lo sabrá. Como dijiste sin, str
también hará el trabajo :) @MehdiDehghani
He usado este método con éxito:
System.Reflection.Assembly.GetExecutingAssembly().CreateInstance(string className)
Deberá convertir el objeto devuelto en el tipo de objeto deseado.
Probablemente mi pregunta debería haber sido más específica. De hecho, conozco una clase base para la cadena, así que la resolví:
ReportClass report = (ReportClass)Activator.CreateInstance(Type.GetType(reportClass));
La clase Activator.CreateInstance tiene varios métodos para lograr lo mismo de diferentes maneras. Podría haberlo lanzado a un objeto, pero lo anterior es de gran utilidad para mi situación.
Sé que llego tarde al juego ... pero la solución que estás buscando podría ser la combinación de lo anterior, y el uso de una interfaz para definir tus objetos de acceso público.
Luego, si todas las clases que se generarían de esta manera implementan esa interfaz, puede convertir como tipo de interfaz y trabajar con el objeto resultante.
Para crear una instancia de una clase desde otro proyecto en la solución, puede obtener el ensamblado indicado por el nombre de cualquier clase (por ejemplo, BaseEntity) y crear una nueva instancia:
var newClass = System.Reflection.Assembly.GetAssembly(typeof(BaseEntity)).CreateInstance("MyProject.Entities.User");
Por ejemplo, si almacena valores de varios tipos en un campo de base de datos (almacenado como una cadena) y tiene otro campo con el nombre del tipo (es decir, String, bool, int, MyClass), entonces, a partir de los datos de ese campo, podría, posiblemente, cree una clase de cualquier tipo con el código anterior y complétela con el valor del primer campo. Esto, por supuesto, depende del tipo que esté almacenando con un método para analizar cadenas en el tipo correcto. Lo he usado muchas veces para almacenar la configuración de preferencias del usuario en una base de datos.
ReportClass report = (ReportClass)Activator.CreateInstance(Type.GetType(reportClass));
¿Por qué quieres escribir un código como este? Si tiene una clase 'ReportClass' disponible, puede instanciarla directamente como se muestra a continuación.
ReportClass report = new ReportClass();
El código ReportClass report = (ReportClass)Activator.CreateInstance(Type.GetType(reportClass));
se utiliza cuando no tiene disponible la clase necesaria, pero desea crear una instancia o invocar un método de forma dinámica.
Quiero decir que es útil cuando conoces el ensamblado, pero al escribir el código no tienes la clase ReportClass
disponible.