C# 11 : fonctionnalités essentielles à connaître

C# 11 apporte des améliorations de productivité et de lisibilité. Ce tip couvre les points saillants avec exemples concis pour une adoption rapide.

Fonctionnalités introduites

Cas d’usage

Raw string literals (chaînes brutes)

Multiligne, pas d'échappement d'anti‑slash ou de guillemets — idéal pour JSON, regex, snippets.

// Raw strings: use triple quotes """ ... """
var json = """
{
  "name": "Craftsman",
  "tags": [\"csharp\", \"tips\"]
}
""";

// Interpolation enabled by doubling $ and quotes
var name = "Dotnet";
var s = $$"""
Hello {name}!
Path: C:\\data\\file.txt
""";
Required members (membres requis)

Forcent l'initialisation des propriétés lors de l'instanciation pour éviter les objets incomplets.

public class User
{
    public required string Name { get; init; }
    public required string Email { get; init; }
}

// Compile-time error if Name/Email are missing
var u = new User { Name = "Ada", Email = "ada@example.com" };
List patterns (patterns de liste)

Exemple concret: router simple qui fait du matching sur les segments d'URL (préfixe, suffixe, capture du reste).

static string HandleRoute(string path)
{
    var segments = path.Trim('/').Split('/', StringSplitOptions.RemoveEmptyEntries);
    return segments switch
    {
        ["products"] => "ListProducts",
        ["products", "new"] => "CreateProduct",
        ["products", var id] => $"GetProduct({id})",
        ["users", "me"] => "GetCurrentUser",
        ["users", var id, "orders", .. var rest] => $"UserOrders({id})/{string.Join('/', rest)}",
        [] => "Home",
        _ => "NotFound"
    };
}

// Exemples
// HandleRoute("/") => Home
// HandleRoute("/products") => ListProducts
// HandleRoute("/products/42") => GetProduct(42)
// HandleRoute("/users/me") => GetCurrentUser
// HandleRoute("/users/7/orders/history") => UserOrders(7)/history

Autres fonctionnalités

Generic math (interfaces avec membres statiques abstraits)

Écrivez des fonctions numériques génériques sans surcharge: une seule implémentation pour int, double, decimal…

using System.Numerics;

// Generic add using INumber<T>
static T Add<T>(T a, T b) where T : INumber<T>
{
    return a + b;
}

var i = Add(1, 2);
var d = Add(1.5, 2.5);
Littéraux UTF-8 (u8)

Construisez rapidement des spans d'octets pour l'I/O réseau et les parsers.

// UTF-8 string literal
ReadOnlySpan<byte> payload = "Hello, UTF-8!"u8;

// Use with I/O APIs expecting spans
Console.WriteLine(System.Text.Encoding.UTF8.GetString(payload));
Types à portée fichier (file)

Limitez la visibilité d'un type au fichier courant pour éviter les collisions de noms.

// File-scoped type
file class HiddenHelper
{
    public static string Value => "Only in this file";
}

public class VisibleType { }

Résumé

Adoptez progressivement ces features là où elles simplifient le code et sécurisent l'API.

Avantages
  • Lisibilité accrue (raw strings, patterns)
  • API plus sûres (required)
  • Moins de bruit syntaxique
Inconvénients
  • Nécessite .NET SDK récent
  • Interop avec anciens analyzers/outils parfois à ajuster

Bonnes pratiques

  • Activez les analyzers et warnings as errors pour fiabiliser required
  • Préférez les raw strings pour JSON/regex plutôt que concaténations
  • Gardez les patterns lisibles (évitez les motifs trop denses)
Sources : Documentation officielleÉcrit le 2025-08-24