2つのリストや配列を結合する際、単にデータを連結するのではなく「重複を取り除いて一意なリストを作りたい」というケースがあります。このような集合演算(和集合)を行うために、LINQにはUnionメソッドが用意されています。
今回は、複数のメーリングリストを統合して、重複のない送信先リストを作成するシナリオを題材に、Unionメソッドの挙動と使い方を解説します。
Unionメソッドの概要
Unionメソッドは、2つのシーケンス(コレクション)の和集合を返します。数学的な「A ∪ B」と同様に、以下の特性を持ちます。
- 2つのリストを結合する: 元のリストと追加したいリストの要素を合わせます。
- 重複を自動的に削除する:
- 片方のリスト内に既にある重複も削除されます。
- 両方のリストに共通して存在する要素は、1つだけが残ります。
単純な連結を行うConcatメソッドとは異なり、結果が一意(ユニーク)であることが保証される点が特徴です。
実践的なコード例:メーリングリストの統合
以下のコードは、「キャンペーンA」と「キャンペーンB」の登録者リスト(メールアドレス)を統合し、全登録者へのお知らせメールを送るためのマスターリストを作成する例です。
using System;
using System.Collections.Generic;
using System.Linq;
namespace MarketingSystem
{
class Program
{
static void Main()
{
// シナリオ:
// 2つの異なるキャンペーンで収集したメールアドレスリストがある。
// 両方のリストには重複するアドレスが含まれている可能性がある。
// 全員に1通だけメールを送るために、重複のないリストを作成したい。
// キャンペーンAの登録者リスト(一部重複あり)
var campaignASubscribers = new[]
{
"alice@example.com",
"bob@example.com",
"charlie@example.com",
"alice@example.com" // リスト内での重複
};
// キャンペーンBの登録者リスト
var campaignBSubscribers = new[]
{
"bob@example.com", // Aとの重複
"dave@example.com",
"eve@example.com"
};
// 1. Unionを使用して和集合を取得
// - campaignASubscribers内の重複("alice")が除去される
// - 両方に存在する("bob")も1つに統合される
var masterList = campaignASubscribers.Union(campaignBSubscribers);
// 2. 見やすくするためにアルファベット順にソート
// Unionの結果は順序が保証されないため、必要に応じてOrderByを使用します。
var sortedMasterList = masterList.OrderBy(email => email);
// 結果の出力
Console.WriteLine("--- 送信先マスターリスト ---");
Console.WriteLine(string.Join(", ", sortedMasterList));
}
}
}
実行結果
--- 送信先マスターリスト ---
alice@example.com, bob@example.com, charlie@example.com, dave@example.com, eve@example.com
技術的なポイントと注意点
1. 重複排除の仕組み
Unionはデフォルトで、要素の型(この場合はstring)のデフォルトの比較ロジックを使用して一致判定を行います。文字列の場合、大文字と小文字は区別されます(例:”User@example.com” と “user@example.com” は別物として扱われます)。大文字小文字を無視して結合したい場合は、Unionの第2引数にStringComparer.OrdinalIgnoreCaseなどを渡す必要があります。
2. Concatとの違い
要素を結合するメソッドとしてConcatがありますが、こちらは「単純な連結」を行います。
- Union: 重複を排除する(集合和)。処理コストは
Concatより高くなる傾向があります。 - Concat: 重複を許可してそのままつなげる。処理は高速です。
要件に応じて、「重複があってもよいか(ログの結合など)」あるいは「重複は許されないか(メール送信など)」で使い分けてください。
3. 遅延実行
Unionメソッドは遅延実行(Deferred Execution)されます。実際に結合処理が行われるのは、foreachで列挙したり、ToListやToArrayなどを呼び出したりしたタイミングです。
まとめ
Unionメソッドを使用することで、複数のデータソースから重複のない一意なリストを簡単に作成できます。特に、マージ処理において手動で重複チェックを行うコードを書く必要がなくなり、可読性と安全性が向上します。リストの結合が必要な場面では、重複の扱いを考慮した上でUnionの採用を検討してください。
