3
public interface ILovable<T> where T : IEquatable<T>
{
    T Care(T t);
}

public class Me : ILovable<int>
{
    public int Care(int i)
    {
        return i;
    }
}

上記があるとしましょう。以下の関数は失敗します:

private static void Colour<T>(ILovable<T> me) where T : IEquatable<T>
{
    var z = me.Care(1); //cannot convert from 'int' to 'T'
}

上記のコードの失敗は何ですか?ILovable<T>Care取り込む機能がTありIEquatable<T>ます。上記の関数では、同じ関数を呼び出して、型であるものCareを渡します。やっぱりです。TintintIEquatable<int>

私は何が間違っているのですか?それを修正するための回避策はありますか?

4

5 に答える 5

3

メソッドシグネチャはを指定せずILovable<int>、を指定しますILovable<T>。たとえば、これは機能します。

private static void Colour(ILovable<int> me)
{
    var z = me.Care(1); //cannot convert from 'int' to 'T'
}

T問題は、コンパイラがそれがあなたの例の「int」であることを知らないことです。制約を満たす任意のタイプにすることができます。これが機能する別の方法です:

private static void Colour<T>(ILovable<T> me, T valueToCareAbout) where T : IEquatable<T>
{
    var z = me.Care(valueToCareAbout);
}
//use like this
Colour(me, 1);
于 2012-12-29T14:21:14.847 に答える
1

私が得るエラーは次のとおりです。

Argument type 'int' is not assignable to parameter type 'T'

meこれは、をとして定義しているためだと確信していますILovable<T>Meしたがって、 intがとして定義されているタイプには自動的に解決されませんT

:としてMe定義Tされているため、これによりエラーが修正されます。int

private static void Colour<T>(Me me) where T : IEquatable<T>
        {
            var z = me.Care(1); 
        }
于 2012-12-29T14:20:33.623 に答える
1

これは、メソッドColorがILovable <T>型のパラメーターがあると言っているのに対し、Tは後で解決されるため、コンパイル時にTがint型であることをメソッドに伝えます。

したがって、パラメータとしてILovableを渡し、Tがintであることを被付与者に渡します。

void Colour<T>(ILovable<int> me)

またはタイプMeを直接渡す

void Colour<T>(Me me)

それ以外の場合はme.Careは、タイプTがintとして特定されていないことを期待しているためです。

于 2012-12-29T14:25:24.633 に答える
1

以下を変更

private static void Colour<T>(ILovable<T> me) where T : IEquatable<T>

private static void Colour<Int32>(ILovable<int> me) 

以上が機能します。


今、神秘の部分

フォロー中にエラーが発生します

private static void Colour<T>(ILovable<T> me) where T : IEquatable<T>

Careを期待しているのでT、あなたはを提供していintます。
と同じです

Care((T)1)

また

 T t = (T)1; //This is the cause of error as int cannot be changed to T. Remember Int32 is sealed so T cannot derive from int

 Care(t); // This is fine

上記の作業を行うにTは、する必要がありintます。そのためには、Colurメソッドの構文は次のようになります。

   private static void Colour<Int32>(ILovable<int> me) 

文字列をに渡したい場合はCare、でTある必要がありますstring

  private static void Colour<string>(ILovable<string> me) 
  {
     me.Care("Hello");
  }

ここで、Tを修正する必要がある場合、定義でTがまったく必要な理由が疑問になりColourます。

回答->非封印クラスの継承型を処理しない場合。

于 2012-12-29T17:37:02.727 に答える
0

簡単な答えは、ジェネリックメソッド(またはクラス)内の型の変数をTより派生型でオーバーライドすることはできません。コンパイラTは、より派生型(この場合Tint)であることを明示的に認識していないためT、他のより派生型である可能性があるためです。実行時に入力します。

長い答え:me変数は型ILovable<T>です。現在me.Care、関数はで指定されたタイプのパラメーターを期待していILovable<T>ますTCare関数の外にはT何でもかまいませんIEquatable<T>ので、int大丈夫です。ただし、関数内では、別の派生型ではなく、Tただである必要があります。そうしないと、次のようなシナリオでランタイムエラーが発生します。TIEquatable<T>

private static void Colour<T>(ILovable<T> me) where T : IEquatable<T>
{
    var z = me.Care(1); 
}

...

Colour("");

現在、Tを呼び出すときは文字列Colour("")です。です。me_ ILovable<string>したがってme.Care、関数はパラメータとしてaを期待stringしますが、提供されるのintは災害です。

于 2012-12-31T02:47:51.897 に答える