【入門編】Dart 3のパターンマッチングにおける「論理演算パターン」の活用術 – Dart コア文法・オブジェクト指向・Null安全解析バイブル

こんにちは!FlutterやDartのコードを日々書いていく中で、「もっとスマートに条件分岐やバリデーションを書きたいな」と感じたことはありませんか?

他の言語、例えばTypeScriptやRustなどでパターンマッチングの便利さを知っている方なら、「Dart 3のパターンマッチングはどう使うんだろう?」とワクワクしているかもしれませんね。

今回は、Dart 3で導入された強力な武器である「論理演算パターン(AND / OR パターン)」にフォーカスして、複雑なデータ構造のバリデーションを美しく、そして一撃でクリアにするテクニックを伝授します。
ここをクリアすれば、あなたのDartコードは一段と洗練されますよ。一緒にマスターしていきましょう!

—

1. Dart 3のパターンマッチングとは?(ざっくりおさらい)

これまでのDartでは、複雑なオブジェクトのデータをチェックするときに、何度も`if`文やプロパティのアクセスを繰り返す必要がありましたよね。

// 昔ながらの書き方(少し冗長ですよね)
if (user != null) {
if (user.age >= 18) {
if (user.status == ‘active’ || user.status == ‘pending’) {
// 処理…
}
}
}

Dart 3で導入されたパターンマッチングを使えば、この「データの形そのもの」を表現して、変数にマッチするかどうかを判定できるようになりました。その中でも、複数の条件を組み合わせる論理演算パターン(`&&` と `||`)は、実務のバリデーションで爆発的な威力を発揮します。

—

2. 論理演算パターンの基本:OR (`||`) と AND (`&&`)

まずは、論理演算パターンの基本的な姿を見てみましょう。パターンマッチングの中では、論理演算子は次のような意味を持ちます。

  • OR パターン (`pattern1 || pattern2`): どちらか一方のパターンにマッチすればOK。
  • AND パターン (`pattern1 && pattern2`): 両方のパターンに同時にマッチする必要がある。

イメージ図:データのチェックフロー

[入力データ] ──> ( パターン A || パターン B ) ──> どちらか一致すればOK!
[入力データ] ──> ( 条件 X && 条件 Y ) ──> 両方満たせばOK!

では、具体的なコードでその動きを確認してみましょう。

—

3. 実践!複雑なバリデーションを一行で書く

例えば、ECサイトのユーザー情報を想像してください。
「VIP会員、または年齢が20歳以上かつアクティブなユーザー」という、少し入り組んだ条件をバリデーションしたいとします。

これをDart 3の `switch` 式と論理演算パターンを使って書くと、こうなります。

// ユーザーを表すレコード(あるいはクラス)
class User {
final String name;
final int age;
final String membership; // ‘vip’, ‘regular’, ‘guest’
final bool isActive;

User(this.name, this.age, this.membership, this.isActive);
}

void validateUser(User user) {
// switch式とパターンマッチングの組み合わせ
String accessLevel = switch (user) {
// 【ORパターンの活用】 VIP会員、または (20歳以上かつアクティブ) の場合
(var u) when u.membership == ‘vip’ || (u.age >= 20 && u.isActive)
=> ‘フルアクセス許可’,

// それ以外
_ => ‘アクセス制限中’,
};

print(‘${user.name}さん: $accessLevel’);
}

void main() {
// テストデータの作成
var alice = User(‘Alice’, 17, ‘vip’, false); ; // VIPなのでOK
var bob = User(‘Bob’, 22, ‘regular’, true); ; // 20歳以上かつアクティブなのでOK
var charlie = User(‘Charlie’, 19, ‘regular’, true); // 条件を満たさないのでNG

validateUser(alice); // 出力: Aliceさん:フルアクセス許可
validateUser(bob); // 出力: Bobさん:フルアクセス許可
validateUser(charlie); // 出力: Charlieさん:アクセス制限中
}

ここで注目してほしいのは、条件判定の部分です。
`||`(OR)と `&&`(AND)を組み合わせることで、本来ならネスト(入れ子)になりがちな複雑なビジネスロジックを、直感的な一行の式として表現できていますよね。

—

4. さらにスマートに!オブジェクトパターンとの組み合わせ

Dart 3の真骨頂は、オブジェクトのプロパティを直接分解(Destructuring)しながら、論理演算を適用できる点にあります。先ほどのコードを、もっとDartらしく洗練させてみましょう。

void smartValidate(User user) {
// オブジェクトのプロパティを直接パターンマッチングにかける
final message = switch (user) {
// membershipが ‘vip’、あるいは (ageが20以上 かつ isActiveがtrue)
(User(membership: ‘vip’) || User(age: >= 20, isActive: true))
=> ‘特権ルートを通ります’,

_ => ‘一般ルートを通ります’,
};

print(message);
}

どうですか?わざわざ一時変数 `u` を経由しなくても、データの構造(`User(age: >= 20, …)`)そのものに条件(関係演算子 `>=`)を組み込み、それを `||` で繋ぐことができています。これが、Dart 3が提供するモダンでエレガントな世界観です。

—

5. 初学者が陥りやすい文法エラーと注意点

新しい機能を学ぶとき、誰もが一度はハマるポイントがあります。ここで先回りして注意点を確認しておきましょう。

注意点1: 変数のバインド(束縛)スコープに気をつける

ORパターン (`||`) の左右で、異なる変数名に値をバインドしようとすると、コンパイルエラーになります。ORの性質上、「どちらのルートを通るかによって作られる変数が変わる可能性がある」ためです。

// ❌ やってはいけない例
// 左右で異なる変数をキャプチャしようとするとDart VMが混乱します
switch (number) {
case int x || String x: // OKな場合もありますが、複雑な構造では制限があります
print(x);
break;
}

解決策: ORパターンの左右では、同じ構造や同じ型の変数を扱うか、純粋に値の比較(定数パターンや関係演算子)に留めるのが安全です。

注意点2: 網羅性チェック(Exhaustiveness Checking)を忘れない

Dart 3の `switch` 式は非常に優秀で、「すべてのケースを網羅しているか」をコンパイル時にチェックしてくれます。もし論理演算パターンを使っていて、意図せず「どのパターンにも当てはまらない隙間」ができてしまうと、コンパイラに怒られてしまいます。

必ず最後に `_ => …` (デフォルトケース)を用意して、安全ネットを張る癖をつけておきましょう。

—

まとめ:ここをクリアすればDartの基本はバッチリ!

今回は、Dart 3のパターンマッチングにおける「論理演算パターン」の活用術をご紹介しました。

  • ORパターン (`||`) で「これ、またはあれ」という柔軟な条件分岐ができる。
  • ANDパターン (`&&`) と組み合わせることで、複雑なバリデーションをフラットに記述できる。
  • オブジェクトの構造分解と組み合わせることで、コードの量が劇的に減り、可読性が跳ね上がる。

最初は見慣れない構文に戸惑うかもしれませんが、一度この書き方に慣れると、もう以前の冗長な `if-else` の世界には戻れなくなりますよ。

ぜひ今日のコードを手元の開発環境で動かして、そのスッキリ感を体感してみてくださいね。
あなたのDartマスターへの道を、これからも応援しています!

タイトルとURLをコピーしました