30 votes

C# Générique Constructeur Statique

Un constructeur statique sur une classe générique être exécutée pour chaque type vous passez dans le paramètre générique comme ceci:

 class SomeGenericClass<T>
 {
      static List<T> _someList;
      static SomeGenericClass()
      {
          _someList = new List<T>();
      }
 }

Existe-il des inconvénients à l'utilisation de cette approche?

39voto

Mark Byers Points 318575

Oui, le constructeur statique sera appelée une fois pour chaque fermée type de classe (le type créé lorsque vous spécifiez le type des paramètres). Voir le C# 3 spécification, §10.12 constructeurs Statiques.

Le constructeur statique pour une fermeture de classe type s'exécute qu'une fois au plus dans un domaine d'application.

et aussi:

Parce que le constructeur statique est exécutée qu'une seule fois pour chaque construit fermé le type de classe, c'est un endroit commode à appliquer au moment de l'exécution des vérifications sur le type de paramètre qui ne peut pas être vérifié au moment de la compilation par les contraintes (§10.1.5). Par exemple, le type suivant utilise un constructeur statique pour faire valoir ce que de l'argument type est un enum:

class Gen<T> where T: struct
{
    static Gen() {
        if (!typeof(T).IsEnum) {
            throw new ArgumentException("T must be an enum");
        }
    }
}

Il est également pertinent de lire §4.4.2 Ouvert et fermé types:

Au moment de l'exécution, le code à l'intérieur d'un type générique de la déclaration est effectuée dans le contexte d'un type construit fermé qui a été créé par l'application d'arguments de type pour le générique de la déclaration. Chaque paramètre de type dans le genre de type est lié à un particulier de type à l'exécution. Le moment de l'exécution du traitement de toutes les déclarations et les expressions se produit toujours fermés types, et d'ouvrir les types se produit uniquement lors de la compilation de traitement.

Chacun construit fermé de type a son propre ensemble de variables statiques, qui ne sont pas partagées avec d'autres types construits.

Ce programme que vous pouvez exécuter vous-même démontre que le constructeur statique est appelé trois fois, pas seulement une fois:

public class Program
{
    class SomeGenericClass<T>
    {
        static SomeGenericClass()
        {
            Console.WriteLine(typeof(T));
        }
    }

    class Baz { }

    static void Main(string[] args)
    {
        SomeGenericClass<int> foo = new SomeGenericClass<int>();
        SomeGenericClass<string> bar = new SomeGenericClass<string>();
        SomeGenericClass<Baz> baz = new SomeGenericClass<Baz>();
    }
}

Sortie:

Système.Int32
Système.Chaîne
Programme+Baz

2voto

Jouke van der Maas Points 2423

Il va travailler, mais une nouvelle "instance" sera créé pour chaque type d'utilisation.

0voto

Julien Lebosquain Points 20894

Oui, les membres statiques et les constructeurs de types génériques sont spécifiques à un paramètre générique et sera exécutée pour chaque type différent. Il n'y a pas de réels inconvénients. Juste être prudent lors de refactoring d'un non-classe générique dans un générique.

0voto

Giorgi Points 15760

Oui, il sera exécuté pour chaque type de vous, car pour chaque type fourni vous obtenez de type séparé.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X