ProgrammingiOS 開発者

Swiftにおける==演算子とEquatableメソッドの違いを説明してください。カスタム型のインスタンスを比較するための正しい実装は何ですか?

Hintsage AIアシスタントで面接を突破

回答

Swiftでは、==演算子は二つの値の等価性をチェックするために使用されます。この演算子をカスタム型で使用するには、その型がEquatableプロトコルに準拠し、静的関数==を実装する必要があります。

実装は対称的で推移的であるべきです。例えば:

struct Person: Equatable { let name: String let age: Int static func ==(lhs: Person, rhs: Person) -> Bool { return lhs.name == rhs.name && lhs.age == rhs.age } }

自分の型が==を実装していない場合、二つのそれらのインスタンスを比較しようとするとコンパイルエラーが発生します。

挑戦的な質問

質問: 構造体またはクラスがEquatableプロトコルを継承している場合、なぜ時々==演算子を明示的に実装する必要がないのでしょうか?

回答: すべてのプロパティがEquatableに準拠している構造体の場合、Swiftは自動的に==演算子の実装を合成します。しかし、型にEquatableでないプロパティがある場合や、カスタム継承を持つクラスの場合、合成は行われず、手動で演算子を実装する必要があります。

struct Point: Equatable { var x: Int var y: Int // ==の実装は不要、これは自動的に合成される }

この分野の細かい点を知らないことで発生した実際のエラーの例。


物語

あるプロジェクトで、開発者が既にEquatableに準拠している構造体にUIImage型のプロパティを追加しました。コンパイルエラーが発生したのは、UIImageEquatableを実装していなかったためで、つまり構造体に自動的に==を合成することができませんでした。解決策は、ロジックにとって重要なプロパティのみを比較するように==演算子を手動で実装することです。


物語

新たなプロパティを構造体に追加したが、それをカスタム==演算子に追加するのを忘れたためエラーが発生しました。これにより、コレクションを扱う際のロジックが正しくなくなり、ユーザーフィルターにバグが発生しました。


物語

プロジェクトにEquatableを実装していないカスタムクラスが書かれましたが、それをSetで使用しようとしました。これにより、Setは要素が一意である必要があるため(したがって、Equatableが必要)、ランタイムエラーが発生しました。