.NET Framework
Types personnalisés
Recherche…
Remarques
Généralement, une struct
est utilisée uniquement lorsque les performances sont très importantes. Étant donné que les types de valeur vivent sur la pile, ils peuvent être accédés beaucoup plus rapidement que les classes. Cependant, la pile a beaucoup moins de place que le tas, donc les structures doivent rester petites (Microsoft recommande la struct
prend pas plus de 16 octets).
Une class
est le type le plus utilisé (parmi ces trois) en C # et correspond généralement à ce que vous devez faire en premier.
Une enum
est utilisée chaque fois que vous pouvez avoir une liste distincte et clairement définie d'éléments à définir une seule fois (au moment de la compilation). Les énumérations sont utiles aux programmeurs en tant que références légères à certaines valeurs: au lieu de définir une liste de variables constant
à comparer, vous pouvez utiliser un enum et obtenir un support Intellisense pour vous assurer de ne pas utiliser accidentellement une mauvaise valeur.
Définition de structure
Les structures héritent de System.ValueType, sont des types de valeur et vivent dans la pile. Lorsque les types de valeur sont passés en paramètre, ils sont transmis par valeur.
Struct MyStruct
{
public int x;
public int y;
}
Passé par valeur signifie que la valeur du paramètre est copiée pour la méthode et que toute modification apportée au paramètre dans la méthode n'est pas répercutée en dehors de la méthode. Par exemple, considérez le code suivant, qui appelle une méthode nommée AddNumbers
, en transmettant les variables a
et b
, de type int
, qui est un type Value.
int a = 5;
int b = 6;
AddNumbers(a,b);
public AddNumbers(int x, int y)
{
int z = x + y; // z becomes 11
x = x + 5; // now we changed x to be 10
z = x + y; // now z becomes 16
}
Même si nous avons ajouté 5 à x
dans la méthode, la valeur d' a
reste inchangé, parce qu'il est un type de valeur, et cela signifie que x
était une copie d' a
« valeur s, mais pas vraiment a
.
Rappelez-vous que les types de valeurs vivent dans la pile et sont transmis par valeur.
Définition de classe
Les classes héritent de System.Object, sont des types de référence et vivent sur le tas. Lorsque les types de référence sont passés en paramètre, ils sont transmis par référence.
public Class MyClass
{
public int a;
public int b;
}
Passé par référence signifie qu'une référence au paramètre est transmise à la méthode et que toute modification apportée au paramètre sera répercutée en dehors de la méthode lors de son retour, car la référence est exactement le même objet en mémoire . Utilisons le même exemple qu'auparavant, mais nous allons "envelopper" les int
dans une classe en premier.
MyClass instanceOfMyClass = new MyClass();
instanceOfMyClass.a = 5;
instanceOfMyClass.b = 6;
AddNumbers(instanceOfMyClass);
public AddNumbers(MyClass sample)
{
int z = sample.a + sample.b; // z becomes 11
sample.a = sample.a + 5; // now we changed a to be 10
z = sample.a + sample.b; // now z becomes 16
}
Cette fois, lorsque nous avons modifié sample.a
à 10
, la valeur de instanceOfMyClass.a
change également , car elle a été transmise par référence . Passé par référence signifie qu'une référence (parfois aussi appelée pointeur ) à l'objet a été transmise à la méthode, au lieu d'une copie de l'objet lui-même.
Rappelez-vous que les types de référence résident sur le tas et sont transmis par référence.
Enum Définition
Un enum est un type spécial de classe. Le mot clé enum
indique au compilateur que cette classe hérite de la classe System.Enum abstraite. Les énumérations sont utilisées pour des listes distinctes d'éléments.
public enum MyEnum
{
Monday = 1,
Tuesday,
Wednesday,
//...
}
Vous pouvez considérer une énumération comme un moyen pratique de mapper des constantes à une valeur sous-jacente. L'énumération définie ci-dessus déclare des valeurs pour chaque jour de la semaine et commence par 1
. Tuesday
deviendrait alors automatiquement mappé sur 2
, Wednesday
à 3
, etc.
Par défaut, les énumérations utilisent int
comme type sous-jacent et commencent à 0, mais vous pouvez utiliser l'un des types intégraux suivants: byte, sbyte, short, ushort, int, uint, long, or ulong
, et pouvez spécifier des valeurs explicites pour tout article. Si certains éléments sont explicitement spécifiés, mais que d'autres ne le sont pas, chaque élément après le dernier défini sera incrémenté de 1.
Nous utiliserons cet exemple en lançant une autre valeur à un MyEnum comme ceci:
MyEnum instance = (MyEnum)3; // the variable named 'instance' gets a
//value of MyEnum.Wednesday, which maps to 3.
int x = 2;
instance = (MyEnum)x; // now 'instance' has a value of MyEnum.Tuesday
Un autre type d'énumération, bien que plus complexe, s'appelle Flags
. En décorant un enum avec l'attribut Flags
, vous pouvez affecter une variable à plusieurs valeurs à la fois. Notez que pour ce faire, vous devez définir des valeurs explicitement dans la représentation de base 2.
[Flags]
public enum MyEnum
{
Monday = 1,
Tuesday = 2,
Wednesday = 4,
Thursday = 8,
Friday = 16,
Saturday = 32,
Sunday = 64
}
Vous pouvez maintenant comparer plusieurs valeurs à la fois, en utilisant des comparaisons par bit ou, si vous utilisez .NET 4.0 ou une version ultérieure, la méthode Enum.HasFlag
.
MyEnum instance = MyEnum.Monday | MyEnum.Thursday; // instance now has a value of
// *both* Monday and Thursday,
// represented by (in binary) 0100.
if (instance.HasFlag(MyEnum.Wednesday))
{
// it doesn't, so this block is skipped
}
else if (instance.HasFlag(MyEnum.Thursday))
{
// it does, so this block is executed
}
Étant donné que la classe Enum est sous- System.ValueType
de System.ValueType
, elle est traitée comme un type de valeur et transmise par valeur et non par référence. L'objet de base est créé sur le tas, mais lorsque vous transmettez une valeur enum à un appel de fonction, une copie de la valeur utilisant le type de valeur sous-jacent de Enum (généralement System.Int32) est insérée dans la pile. Le compilateur suit l'association entre cette valeur et l'objet de base créé sur la pile. Voir Classe ValueType (System) (MSDN) pour plus d'informations.