ホームページ > バックエンド開発 > C++ > C# で派生型から基本ジェネリック型へのキャストが失敗するのはなぜですか?

C# で派生型から基本ジェネリック型へのキャストが失敗するのはなぜですか?

Patricia Arquette
リリース: 2025-01-06 02:19:40
オリジナル
551 人が閲覧しました

Why Does Casting from a Derived to a Base Generic Type Fail in C#?

派生型から基本ジェネリック型へのキャスト: 非互換性の詳細を調べる

C# では、ジェネリック型の継承モデルについてよく疑問が生じます。派生型から基本型へのキャスト。このクエリは、根底にある複雑さと、派生クラスから基本クラスへの直接的なキャストが失敗する理由を調査します。

キャストの謎

次のコード スニペットを考えてみましょう。

public abstract class EntityBase { }
public class MyEntity : EntityBase { }

public abstract class RepositoryBase<T> where T : EntityBase { }
public class MyEntityRepository : RepositoryBase<MyEntity> { }
ログイン後にコピー

さて、問題を調べてみましょうline:

MyEntityRepository myEntityRepo = GetMyEntityRepo(); // whatever
RepositoryBase<EntityBase> baseRepo = (RepositoryBase<EntityBase>)myEntityRepo;
ログイン後にコピー

このコードを実行すると、ランタイム例外が発生します。このキャストの試行はなぜ失敗しますか?

汎用差異: 互換性の幻想

直感的には、MyEntityRepository のような派生クラスもその基本クラスの型であると想定できます。クラス、RepositoryBase。ただし、ジェネリックスの領域では、この仮定が常に有効であるとは限りません。

ジェネリックの差異とは、ジェネリック型がその型パラメーターを多かれ少なかれ派生型で置き換えることができる機能を指します。残念ながら、C# は、特定の特定のシナリオで限定された差異のみをサポートします。

この例では、RepositoryBaseは MyEntityRepository の基本クラスではありません。これは、型パラメーター T がその基本型に関して共変でも反変でもないためです。

共分散: 一方的な旅

共分散により、ジェネリック クラスは参照できるようになります。基本クラスよりも派生した型パラメーター。これは、ジェネリック型が値を返すためにその型パラメーターのみを使用する特定の状況で許可されます。ただし、ここではそうではありません。

反変性: 上り坂の戦い

一方、反変性を使用すると、ジェネリック型で派生度の低い型パラメーターを使用できます。値を受け入れるときは、その基本クラスよりも。しかし、繰り返しになりますが、これはこのコンテキストでは適用できません。

ジェネリック安全性の保護

ジェネリックの分散がないと、派生型から基本型へのキャストは予期せぬ事態を招く可能性があります。動作と潜在的な実行時エラー。たとえば、RepositoryBase がクラスには、MyEntityRepository を RepositoryBase にキャストする、EntityBase 型のエンティティに対してのみ操作できるメソッドがありました。

キャストの落とし穴の回避

ジェネリック型間でキャストする必要がある場合は、ジェネリックの差異の制限を理解することが重要です。これらの落とし穴を回避するには、基本クラスから派生クラスへの明示的なキャストを導入するか、ファクトリー メソッドやブリッジ パターンなどの代替設計パターンを使用することを検討してください。

以上がC# で派生型から基本ジェネリック型へのキャストが失敗するのはなぜですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
著者別の最新記事
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート