Tip
この記事は、少なくとも 1 つのプログラミング言語を既に知っており、C# を学習している開発者向けの 基礎 セクションの一部です。 パターンが初めて使用される場合は、パターン マッチングの概要 から始めます。 サポートされている型と言語の完全な規則については、言語リファレンスの リスト パターン を参照してください。
シーケンスの 図形 は、パターンに必要な監視可能なプロパティのセットです。 これらのプロパティには、要素の数、すべての要素または要素のシーケンス全体に対して書き込まれた要件、および特定のインデックスのマーカー値を含めることができます。 たとえば、図形には、インデックス 0 に "Name" を持つ 2 つの要素が必要な場合や、最初のマーカー、最後のマーカー、それらの間に空でないシーケンスが必要な場合があります。
リスト パターンは、要素数の要件と、順序付けられた位置にある入れ子になったパターンを組み合わせることによって、図形を記述します。 これは、パターンで記述された要件のみをテストします。要素サブパターンは対応する要素をテストしますが、 スライス パターン では、それ以外の一致しない要素のシーケンスを許可またはテストできます。 これらのパーツを使用して、正確なカウントとマーカー値の照合、固定位置での値のキャプチャ、一致しない中間の許可、またはその中間に入れ子になったパターンの適用を行うことができます。
入力のコンパイル時の型が Length または Count プロパティとインデックス付き要素アクセスを提供する場合は、リスト パターンを選択します。これは、 input[index]のように、位置によって要素を取得します。 配列、 List<T>、文字列、スパンは一般的な例です。 コンパイラは、プログラムを実行する前に必要なメンバーを解決する必要があるため、変数の宣言されたコンパイル時の型から適格性を判断します。 ランタイム オブジェクトがインデックス可能なコレクションである場合でも、 IEnumerable<T> インターフェイス自体は、これらのメンバーの代わりに列挙型を提供します。
リスト パターンでは、列挙型の代わりに長さまたはカウントとインデックス付き要素のアクセスが使用されます。 一般的な組み込み型の場合、照合では、すべての要素を反復処理するのではなく、パターンによって名前付けされた位置のみをチェックできます。 これらの操作のコストは、入力の種類によって異なります。 長いコレクションの反復処理には時間がかかる可能性があるため、特定の位置ではなく任意の数の要素を調べる必要がある場合は、ループまたは LINQ を使用します。
ぴったり一致する形に合わせる
次のメソッドは、2 列のヘッダーを認識します。
static bool IsHeader(string[] columns) =>
columns is ["Name", "Score"];
columns式はパターン入力です。
["Name", "Score"] には、2 つの定数パターンが含まれています。 正確なリスト パターンはスライス パターンを省略し、2 つの要素を必要とし、各入れ子になったパターンを同じインデックスの要素に適用します。 このパターンは、正確なカウントと 2 つのマーカー値を持つ図形を表します。インデックス 0 の "Name" とインデックス 1 の "Score" です。 入れ子になった要素パターンは省略可能です。空のリスト パターン [] は、要素を含まないシーケンスを記述し、それに一致します。
図形が要素数と順序付けられた位置の要件を組み合わせた場合に、リスト パターンを選択します。 要素の数だけが重要な場合は、items is { Count: 0 }などのLengthまたはCountプロパティ パターンによって、その意図がより直接的に示されます。
破棄を使用して任意の要素値と一致させる
次のメソッドは、3人の着順から勝者と3位の選手を読み取ります。
static string GetAnnouncements(List<string> finishingOrder) =>
finishingOrder switch
{
[var winner, _, var thirdPlace] =>
$"Winner: {winner}; third place: {thirdPlace}",
_ => "A complete three-runner result isn't available"
};
var winnerパターンとvar thirdPlace パターンはそれぞれ変数を宣言します。 リスト パターンが一致すると、C# はその位置にある一致した要素値を対応する変数に割り当てます。これにより、結果は winner と thirdPlaceを使用できます。 破棄パターン _ は、2 番目の要素を受け取り、その値を破棄します。 この図形には 3 つの要素が必要であり、1 番目と 3 番目の位置に特定の意味が与えられますが、どの位置でも特定の値は必要ありません。
固定位置が安定した意味を持つ場合は、このフォームを選択します。 任意の数の要素を調べたり、シーケンスを変換したり、シーケンス全体を検索したり、集計を実行したりする必要がある場合は、ループまたは LINQ を使用します。
スライス パターンを使用して残余の要素を許可する
この簡略化された例では、コマンド ラインは --verbose で始まり、他の引数を含めることができます。これは、入力ファイル名で終わるものと見なされます。 次のメソッドは、最後の位置にファイル名を持つ図形を認識し、その値をキャプチャします。
static string GetInputFile(string[] arguments) =>
arguments switch
{
["--verbose", .., var fileName] => $"Verbose processing: {fileName}",
[.., var fileName] => $"Processing: {fileName}",
[] => "No input file was provided"
};
スライス パターン..では、最初の要素パターンと最後の要素パターンの間に 0 個以上の残りの要素を使用できます。 リスト パターンには、最大 1 つのスライス パターンを含めることができます。 最初のスイッチ アームは、インデックス 0 のマーカー "--verbose" 、最後の位置のファイル名、およびそれらの間の一致しない引数の数の 2 つ以上の要素を持つ図形を記述します。 スタンドアロン スライスでは、これらの中間引数はテストされません。 2 番目のアームは空でない図形を受け取り、最後の要素をキャプチャしますが、空のパターンは要素のないシーケンスを処理します。
スライスは、リスト パターンの先頭、中央、または末尾に表示できます。 可変長シーケンスが図形の一部であるが、周囲の位置のみが要素テストを必要とする場合に使用します。 すべての要素に処理が必要な場合は、通常のイテレーションを使用します。
スライスにパターンを適用する
..で一致するパーツに別のパターンを適用できます。 次のメソッドは、配列が "BEGIN"で始まり、 "END"で終わり、それらの間に少なくとも 1 つの要素があるかどうかをテストします。
static bool HasContent(string[] entries) =>
entries is ["BEGIN", .. { Length: > 0 }, "END"];
外側のパターンでは、最初にインデックス 0 にマーカー "BEGIN" し、最後のインデックスに "END" する必要があります。 その後、プロパティ パターン { Length: > 0 } 、スライスで一致するシーケンスの要件を追加します。少なくとも 1 つの要素を含める必要があります。 これらの要件を組み合わせることで、完全な形状が示されます。 このパターンでは、スライス内の要素の値はテストされません。
スライス サブパターンは、中間部分自体にテストまたはキャプチャが必要な場合にのみ使用します。 境界要素のみが重要な場合は、単純な .. の方が簡単です。
こちらも参照ください
.NET