Come creare una nuova istanza di oggetto da un Tipo

Non sempre si può conoscere il Type di un oggetto in fase di compilazione, ma si può avere bisogno di creare un'istanza del Type. Come si ottiene un'istanza di un nuovo oggetto da un Type?

Soluzione

La classe Activator all'interno dello spazio dei nomi principale System è piuttosto potente.

Ci sono molti sovraccarichi per passare parametri al costruttore e così via. Controlla la documentazione su:

http://msdn.microsoft.com/en-us/library/system.activator.createinstance.aspx>

o (nuovo percorso)

https://docs.microsoft.com/en-us/dotnet/api/system.activator.createinstance>

Ecco alcuni semplici esempi:

ObjectType instance = (ObjectType)Activator.CreateInstance(objectType);

ObjectType instance = (ObjectType)Activator.CreateInstance("MyAssembly","MyNamespace.ObjectType");
Commentari (6)

Un'implementazione di questo problema è tentare di chiamare il costruttore senza parametri di Type:

public static object GetNewObject(Type t)
{
    try
    {
        return t.GetConstructor(new Type[] { }).Invoke(new object[] { });
    }
    catch
    {
        return null;
    }
}

Ecco lo stesso approccio, contenuto in un metodo generico:

public static T GetNewObject()
{
    try
    {
        return (T)typeof(T).GetConstructor(new Type[] { }).Invoke(new object[] { });
    }
    catch
    {
        return default(T);
    }
}
Commentari (1)

Se questo è per qualcosa che sarà chiamato spesso in un'istanza dell'applicazione, è molto più veloce compilare e mettere in cache il codice dinamico invece di usare l'attivatore o ConstructorInfo.Invoke(). Due facili opzioni per la compilazione dinamica sono le Linq Expressions compilate o alcuni semplici opcodes IL e DynamicMethod. In entrambi i casi, la differenza è enorme quando si inizia a entrare in cicli stretti o chiamate multiple.

Commentari (1)