8

簡単なジェネリック関数を作りたい

void Assign<T>(out T result) 
{
  Type type = typeof(T);
  if (type.Name == "String")
  {
     // result = "hello";
  }
  else if (type.Name == "Int32")
  {
     // result = 100;
  } 
  else result = default(T);
}

使用法:

int value;
string text;

Assign(value); // <<< should set value to 100
Assign(text); // <<< should set text to "hello"

私の質問は、これらの値を設定するようにコードをどのようにプログラムするかです。コメントセクションに欠落しているコード。

助けてくれてありがとう。

4

4 に答える 4

16

この場合、ボクシングを避けるためにやっているのではないでしょうか。詳細情報なしで言うのは難しいですが、この特定の例では、メソッドのオーバーロードを使用する方がはるかに簡単で、おそらくバグが発生しにくいでしょう。

void Assign(out string value)
{
   //...
}

void Assign(out int value)
{
   //...
}

ここで何が問題なのかを具体的に学習するために、オブジェクトを汎用型にキャストする前に、オブジェクトに値をキャストする必要があります。

(T)(object)"hello world!";

どのIMOはかなり厄介で、最後の手段となるはずです。確かに、コードがクリーンになるわけではありません。

ジェネリックパラメーターの型チェックを行うときはいつでも、ジェネリックが問題の正しい解決策ではないことを示す良い兆候です。ジェネリックパラメーター型のチェックを行うと、コードは単純ではなく、より複雑になります。これにより、他のメソッドに誤って影響を与えることなく簡単に変更できる一連の単一のメソッドではなく、1つのメソッドがタイプに基づいてさまざまな動作を担当します。単一責任の原則を参照してください。

于 2009-11-14T22:02:39.117 に答える
3

まず第一に、それは非常に悪いパターンです。この種のパターンは使用しないでください。たぶん、あなたが本当に達成したいことを説明すれば、より良い答えがあるでしょう。

以下のコードは機能しますが、私が言ったように、この方法でコードを書くことは悪い考えです。

    void Assign<T>(out T result) 
    { 
        Type type = typeof(T); 
        if (type.Name == "String") 
        { result = (T) ((object)"hello"); } 
        else if (type.Name == "Int32") 
        { result = (T) ((object)100); } 
        else result = default(T); 
    }

そして使用法:

        int value;
        string text;

        Assign(out value);
        Assign(out text);
于 2009-11-14T22:10:03.870 に答える
1
public T GetObject<T>(string val)
{
    T _object = default(T);
    _object = (T)Convert.ChangeType(val, typeof(T));
    return _object;
}
于 2011-09-07T07:28:54.587 に答える
0

これが1つの方法です:

static void Assign<T>(out T result) { 
    Type type = typeof(T);
    if (type.Name == "String") {
        result = (T)Convert.ChangeType("hello", typeof(T));
    }
    else if (type.Name == "Int32") {
        result = (T)Convert.ChangeType(100, typeof(T));
    }
    else {
        result = default(T);
    }
}

しかし、このコードは非常に悪臭があり、ジェネリックスのポイントに反します(代わりにオーバーロードされたメソッドを使用します)。これが本番コードのどこかに終わらないことを願っています。これは単に教育のためのものです。

于 2009-11-14T22:03:44.863 に答える