.Net 6 : Les nouveautés du C# 10 en un clin d’œil!
Avec l’arrivée de .Net 6, la nouvelle version de C# (10) apporte son lot de nouvelles fonctionnalités. Cet article résume, sans entrer dans les détails, les nouvelles fonctionnalités qui pourront vous être utile dans votre vie de développeur en C#.
Record struct
Apparu en C# 9, le mot-clé permet « record » de créer des objets de types références dont les propriétés sont immutables. Vous pouvez en créer de deux manières, soit via des paramètres, soit via la syntaxe classique avec des propriétés. Via la syntaxe classique, vous pouvez tout de même déclarer que les propriétés sont mutables, mais ce n’est pas ce pourquoi ont été créé les records.
public record Person(string FirstName, string LastName);
// These two declarations correspond to an equivalent object
public record Person {
public string FirstName { get; init; }
public string LastName { get; init; }
}
Depuis C#10, vous pouvez créer des records de type « struct ». Il y a tout de même une différence par rapport aux records de type référence, c’est que par défaut, les propriétés sont mutables.
public record struct Person(string FirstName, string LastName);
// These two declarations correspond to an equivalent object
public record struct Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
}
Pour déclarer les propriétés immutables, il suffit d’ajouter le mot clé readonly devant le mot-clé record.
public readonly record struct Person(string FirstName, string LastName);
// These two declarations correspond to an equivalent object
public record struct Person
{
public string FirstName { get; init; }
public string LastName { get; init; }
}
Et avec C# 10, si vous voulez éviter les confusions, vous pouvez préciser que le record est de type référence, en ajoutant le mot-clé class.
public record class Person(string FirstName, string LastName);
Initialiser par défaut les propriétés d’une struct
Depuis C# 10, vous pouvez créer un constructeur par défaut pour initialiser les propriétés de vos structs.
public struct Person
{
public Person()
{
FirstName = default;
LastName = default;
}
public string FirstName { get; init; }
public string LastName { get; init; }
}
Et vous pouvez aussi directement initialiser une propriété spécifique.
public struct Person
{
public string FirstName { get; init; } = default; // Not allowed in C# 9
public string LastName { get; init; }
}
Instanciation d’une copie d’une struct à l’aide du mot-clé With
En C# 9, en plus de la possibilité de créer des records, vous pouvez créer des copies d’objet record, et modifier la valeur d’une ou plusieurs propriétés à l’aide du mot-clé with.
class Program
{
static void Main(string[] args)
{
var person = new Person("Damien", "VDK");
var person2 = person with {FirstName = "Bill"};
Console.WriteLine((person.FirstName)); // Output Damien
Console.WriteLine((person2.FirstName)); // Output Bill
}
}
public record Person (string FirstName, string LastName);
En C#, 10 vous pouvez maintenant faire la même chose avec les structs.
var person = new Person() { FirstName = "Damien" };
var person2 = person with { FirstName = "Bill" };
Console.WriteLine((person.FirstName)); // Output Damien
Console.WriteLine((person2.FirstName)); // Output Bill
public struct Person
{
public string FirstName { get; init; }
public string LastName { get; init; }
}
String Interpolation et Const
Vous pouvez à présent utiliser le « string interpolation » sur des constantes, à condition que les variables interpolées soient également des constantes.
const string FirstName = "Damien";
const string LastName = "VDK";
const string FullName = $"{FirstName} {LastName}";
Namespace
Si votre fichier ne contient qu’un seul namespace, vous n’avez plus besoin de mettre le contenu du fichier dans des accolades.
namespace DamienVDK.Model;
public class Person {}
Les lignes de code ci-dessus correspondent aux suivantes en C# 9.
namespace DamienVDK.Model
{
public class Person { }
}
Record : Sealed ToString()
En C# 10, vous pouvez à présent rendre la méthode ToString() en tant que « sealed » pour les records.
public record Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
public sealed override string ToString()
{
return $"{FirstName} {LastName}";
}
}
Deconstruct
Avant C# 10, une déconstruction pouvait affecter toutes les valeurs aux variables existantes ou initialiser les variables nouvellement déclarées. Maintenant, vous pouvez mixer les deux.
var person = new Person() { FirstName = "Damien", LastName = "VDK" };
// Allowed in C# 9 AND 10
(string firstName, string lastName) = person;
Console.WriteLine($"{firstName} {lastName}"); // Output = Damien VDK
var newFirstName = string.Empty;
var newLastName = string.Empty;
(newFirstName, newLastName) = person;
Console.WriteLine($"{newFirstName} {newLastName}"); // Output = Damien VDK
// Allowed in C# 10 only
var c10FirstName = string.Empty;
(c10FirstName, string C10LastName) = person;
Console.WriteLine($"{c10FirstName} {c10FirstName}"); // Output = Damien VDK
public class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
public void Deconstruct(out string firstName, out string lastName)
{
firstName = FirstName;
lastName = LastName;
}
}
Global using
De la même manière que pour le « _Imports.razor » en, Blazor, vous pouvez créer un fichier un fichier « cs », peut importe son nom, et y mettre vos nampespaces « globaux ». Ces derniers ne devront donc plus être référencés dans vos autres fichiers.
global using System.Collections.Generic;
global using System.Linq;
global using System.Text;
global using System.Threading.Tasks;
#line
Le mot-clé #line vous permet de modifier le numéro des lignes du compilateur et le nom de fichier pour les erreurs et les avertissements. Une nouvelle forme d’utiliser cette directive a été ajoutée dans C# 10. Ci-dessous, l’exemple présentant cette dernière que vous trouverez sur le site de Microsoft.
#line (1, 1) - (5, 60) 10 "partial-class.g.cs"
/*34567*/int b = 0;
(1,1) – Le premier numéro de ligne et de colonne qui démarre après cette directive.
(5, 60) – Le numéro de ligne et de colonne qui seront utilisés à la fin de cette directive
10 (Optionnel) – Le nombre de colonnes « bypassé » avant de démarrer la numérotation. Dans l’exemple, /*34567*/ ne sera donc pas comptabilisé.
partial-class.g.cs – Le nom du fichier de sortie.
Simplification des Property Pattern
L’utilisation des property pattern a été simplifiée en C#10, si vous souhaitez vérifier une valeur sur un objet enfant.
var person = new Person() { FirstName = "Damien", LastName = "VDK", Language = new Language() { Label = "FR" } };
var person2 = new Person() { FirstName = "Bill", LastName = "Gate", Language = new Language() { Label = "EN" } };
Console.WriteLine(GetHelloPerLanguage(person));
Console.WriteLine(GetHelloPerLanguage(person2));
// Allowed in C#9 AND C#10
string GetHelloPerLanguage(Person person)
{
return person switch
{
{ Language: { Label: "FR" } } => "Bonjour",
{ Language: { Label: "EN" } } => "Hello",
_ => "???"
};
}
// More simpler, but not allowed in C#9
string GetHelloPerLanguageC10(Person person)
{
return person switch
{
{ Language.Label: "FR" } => "Bonjour",
{ Language.Label: "EN" } => "Hello",
_ => "???"
};
}
public class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
public Language Language { get; set; }
}
public class Language
{
public string Label { get; set; }
}
Conclusion
Comme vous pouvez le constater, pas mal de changement pour ce C# 10. Vous pouvez bien entendu retrouver les détails de ces derniers sur le site de Microsoft. N’hésitez pas à donner votre avis en commentaire sur ces nouvelles fonctionnalités, et surtout de partager cet article si vous avez aimé celui-ci 🙂