CSharp 4
Apparence
Les paramètres nommés et optionnels
// cette méthode possède un paramètre optionel par défaut à 7
public void Methode(string param1, int param2 = 7) { ... }
Methode("cinq", 10); // appel classique
// param2 est un paramètre optionel. Il est donc possible de ne pas le spécifier
// il prendra donc sa valeur par défaut 7.
Methode("cinq");
// appel en nommant les paramètres
Methode(param2: 10, param1: "cinq");
// Les valeurs par défaut des paramètres optionnels doivent être des constantes
// voici deux manières d'utiliser un DateTime en paramètre optionnel
public void Methode(DateTime date1 = default(DateTime), DateTime? date2 = null)
{
if (date1 == default(DateTime)) date1 = new DateTime(...);
if (date2 == null) date2 = new DateTime(...);
}
|
Dynamic type
Permet de déclarer des instances dont le type est inconnu à la compilation et sera résolu à l'exécution.
// le type d'instance sera résolu à l'exécution
dynamic instance = ...;
// on peut donc
instance.Methode(); // appeler Methode depuis instance
var v = instance.Propriete; // appeler Propriete depuis instance
var i = instance[0]; // appeler l'index 0 depuis instance
instance("string"); // utiliser instance comme un délégué
|
Covariance et Contra variance des génériques
![]() |
Seulement pour les interfaces et les delegates |
Covariance
Conversion en sortie grâce au mot clé out: interface IMonInterface<out T>
List<string> myStrings = new List<string>();
myStrings.Add("Un");
// variance de type générique, pris en charge à partir de C# 4 (List<string> → IEnumerable<object>)
IEnumerable<object> myObjects = myStrings;
// Ne fonctionne pas avec List<object>, IList<object>
List<object> myObjects = myStrings;
// Cannot implicitly convert type `System.Collections.Generic.List<string>' to `System.Collections.Generic.IList<object>'.
// Ne fonctionne pas avec le boxing (int → object)
List<int> myInts = new List<int>();
myInts.Add(1);
IEnumerable<object> myObjects = myInts;
// Cannot implicitly convert type `System.Collections.Generic.List<int>' to `System.Collections.Generic.IEnumerable<object>'.
|
Contra variance
Conversion en entrée grâce au mot clé in: interface IComparer<in T>
public class C1
{
public string P1 { get; set; }
}
public class C2 : C1
{ }
// classe permettant la comparaison (et donc le tri) entre objets issus de la classe C1
class MyComparer : IComparer<C1>
{
public int Compare(C1 x, C1 y)
{
if (x == null && y == null)
{
return 0;
}
else if (x == null)
{
return -1;
}
else if (y == null)
{
return 1;
}
else
{
return x.P1.ToLower().CompareTo(y.P1.ToLower());
}
}
}
MyComparer comparer = new MyComparer();
List<C1> c1List = new List<C1>();
c1List.Add(new C1() { P1 = "Un" });
c1List.Add(new C1() { P1 = "Deux" });
// tri à l'aide de la classe MyComparer
c1List.Sort(comparer);
// même chode avec C2
List<C2> c2List = new List<C2>();
c2List.Add(new C2() { P1 = "Un" });
c2List.Add(new C2() { P1 = "Deux" });
// tri à l'aide de la classe MyComparer
// on peut ici réutiliser la classe MyComparer grace à la contra variance,
// sinon il aurait fallut écrire une class MyComparerC2 : IComparer<C2>
c2List.Sort(comparer);
|