は、このインタフェースを考えてみましょう。なぜこの共分散宣言はコンパイルされますか?</p> <pre><code>interface Test<out T> where T : struct { } </code></pre> <p>それはエラーや警告なしでコンパイル:
this questionで論じ、そしてthe Covariance and Contravariance FAQで述べたように:
分散は、型パラメータが参照型である場合にのみサポートされています。
なぜ上記のインターフェイスはコンパイルされますか? "out"キーワードに失敗する(または少なくとも警告する)のは意味があります。私は上記の例のout
キーワードを使用すると違いがあるのでしょうか?
更新は:コーダがのために働いていない分散を認識していない場合は
typeof(IDummy).IsAssignableFrom(typeof(MyStruct)); // should return true
typeof(ITest<IDummy>).IsAssignableFrom(typeof(ITest<MyStruct>)); // returns false
:ここでは、上記のインターフェイスを見て気づいていない開発者のためのすり抜けも例誤解を招く行動です2番目の行がout
キーワードのためにtrue
を返すと予想しますが、それは決してありません。 (
ITest<MyStruct> foo = ...;
var casted = (ITest<IDummy>)foo;
私はこれが動作するように期待する:これは、この質問をするために私を促したバグ...
コンパイルが、予期しない結果を生成するコードの別の例正確です参照型への共分散の制限についてはわかりませんが)、System.InvalidCastExceptionが発生します。
その場合、私はそれをコンパイラのバグだと考えます。分散効果のないキーワードを使用することはできません。 – sinelaw
@sinelaw:私はあなたに同意します。私のせい。私はこの機能を設計するときにこれを考慮したことはありません。私のmea culpaについては、http://stackoverflow.com/questions/9353293/c-sharp-variance-annotation-of-a-type-parameter-constrained-to-be-value-typeを参照してください。 –
@EricLippert、ありがとう!あなたが言ったように「おそらくそこには開発者がいて、それが動作すると思うように入力するかもしれない」 - 私はそれが私だと思います。 :) – sinelaw