C#におけるレコード型とオブジェクトの等価性
C# 9.0で導入されたレコード型(record
)は、特に不変性(イミュータブル性)を持つデータ構造として設計されています。レコード型は、クラス型と比較して、オブジェクトの等価性に関して重要な違いがあります。この資料では、レコード型における等価性の扱い方について説明し、==
演算子やReferenceEquals
メソッドとの関係を中心に解説します。
レコード型と値の等価性
サンプルコード
以下は、レコード型を使用してBook
型を定義し、2つの異なるインスタンスが値として等価かどうかを確認するコード例です。
public record Book(string Title);
internal class Program
{
private static void Main(string[] args)
{
// 2つの異なるBookオブジェクトを作成
Book book1 = new Book("同じタイトル");
Book book2 = new Book("同じタイトル");
// ==演算子で比較
Console.WriteLine("book1とbook2は同じですか? " + (book1 == book2)); // True
}
}
結果
このコードを実行すると、以下の出力が得られます。
book1とbook2は同じですか? True
解説
- 値の等価性: レコード型では、デフォルトで「値の等価性」がサポートされています。これは、プロパティの値が同じであれば、オブジェクトが異なるインスタンスであっても
==
演算子で比較した際にTrue
を返すことを意味します。 ==
演算子の動作: レコード型では、==
演算子が自動的にオーバーロードされ、プロパティの値を比較するようになっています。このため、book1
とbook2
は異なるインスタンスですが、同じタイトルを持つため、等価と見なされます。
レコード型と参照の等価性
レコード型でも、必要に応じてオブジェクトの参照が同一であるかを確認することができます。これには、ReferenceEquals
メソッドを使用します。
サンプルコード
public record Book(string Title);
internal class Program
{
private static void Main(string[] args)
{
Book book1 = new Book("同じタイトル");
Book book2 = new Book("同じタイトル");
Book book3 = book1;
Console.WriteLine("book1とbook2は同じ参照ですか? " + ReferenceEquals(book1, book2)); // False
Console.WriteLine("book1とbook3は同じ参照ですか? " + ReferenceEquals(book1, book3)); // True
}
}
結果
このコードを実行すると、以下の出力が得られます。
book1とbook2は同じ参照ですか? False
book1とbook3は同じ参照ですか? True
解説
- 参照の等価性:
ReferenceEquals
メソッドは、2つのオブジェクトが同じメモリ位置を参照しているかどうかを確認します。book1
とbook2
は異なるインスタンスなので、False
を返しますが、book3
はbook1
と同じインスタンスを参照しているため、True
を返します。
レコード型の利点
自動生成されるメンバー
レコード型では、デフォルトで以下のメンバーが自動的に生成されます。
==
演算子Equals
メソッドGetHashCode
メソッド
これにより、オブジェクトの等価性のチェックやハッシュコードの生成が簡単になります。
簡潔さと不変性
- 簡潔さ: レコード型を使用することで、クラス型で必要だった等価性チェックのコードが自動生成され、コードが簡潔になります。
- 不変性: レコード型は通常、イミュータブル(不変)なデータを扱う際に使用されます。プロパティはデフォルトで読み取り専用となります。
まとめ
レコード型は、C#においてオブジェクトの等価性を扱う上で非常に便利な機能を提供します。値の等価性をサポートし、データ構造の比較を簡潔かつ正確に行うことができるため、特に不変のデータ構造を扱うシナリオに適しています。==
演算子とReferenceEquals
メソッドの使い分けを理解することで、より意図的で明確なコードを書くことができるでしょう。
この資料は、レコード型とオブジェクトの等価性に関する基本的な理解を深めることを目的としています。
ディスカッション
コメント一覧
まだ、コメントがありません