2

私はこのコードを持っていると言います:

Dictionary<String, String> myDictionary = new Dictionary<String, String>();
Type[] arguments = myDictionary.GetType().GetGenericArguments();

私のプログラム myDictionary では、不明な型 (デシリアライズされた XML から返されたオブジェクト) ですが、この質問の目的のために、それらは文字列です。私はこのようなものを作成したい:

Dictionary<arguments[0],arguments[1]> mySecondDictionary = new Dictionary<arguments[0],arguments[1]>();

明らかに、うまくいきません。MSDN で検索したところ、Activator クラスを使用していることがわかりましたが、わかりません。たぶん、より高度な誰かが私を少し助けてくれるでしょう。

4

3 に答える 3

1

このアプローチには問題があります。私はそれを説明するために最善を尽くします。最初にクラスを XML にシリアル化し、次に逆シリアル化するプログラムを作成しました。基本的に、クラスはジェネリックであり、リスト(クラスと同じ型)が含まれています。したがって、クラスの型は、string や int などの単純な型から、本のクラスや人物などのより複雑なクラスまで、何でもかまいません。XmlSerializer.Deserialize メソッドを使用してオブジェクトを取得したら、Reflection を使用してオブジェクトを再構築し、リストにアクセスする必要があります。そして、私はそのようにすることはできません。したがって、次のようなものがある場合:

Type classToCreate = typeof(classToBeSerialized<>).MakeGenericType(arguments);
var reconstructedClass = Activator.CreateInstance(classToCreate);

ここで、classToBeSerialized は想定されるクラス (私が話したリストを持っています) であり、returnedObject は XmlSerializer.Deserialize から返されたオブジェクトです。次のようにリストにアクセスしたいと思います。

 ((reconstructedClass)returnedObject).lista

基本的に、リフレクションを使用してオブジェクトをソースにキャストしています。

于 2013-07-07T20:21:20.060 に答える
0

これが古いスレッドであることは知っていますが、似たようなものが必要だったので、それを表示することにしました(Googleについてはご存知でしょう)。

これは基本的に@ user2536272による回答の書き直しです

public object ConstructDictionary(Type KeyType, Type ValueType)
{
    Type[] TemplateTypes = new Type[]{KeyType, ValueType};
    Type DictionaryType = typeof(Dictionary<,>).MakeGenericType(TemplateTypes);

    return Activator.CreateInstance(DictionaryType);
}

public void AddToDictionary(object DictionaryObject, object KeyObject, object ValueObject )
{
    Type DictionaryType = DictionaryObject.GetType();

    if (!(DictionaryType .IsGenericType && DictionaryType .GetGenericTypeDefinition() == typeof(Dictionary<,>)))
        throw new Exception("sorry object is not a dictionary");

    Type[] TemplateTypes = DictionaryType.GetGenericArguments();
    var add = DictionaryType.GetMethod("Add", new[] { TemplateTypes[0], TemplateTypes[1] });
    add.Invoke(DictionaryObject, new object[] { KeyObject, ValueObject });
}
于 2016-07-08T11:32:14.183 に答える
0

特定のタイプからオブジェクトを作成するために、言及したようにアクティベータークラスを使用できます。MakeGenericTypeメソッドを使用すると、タイプの配列を汎用オブジェクトのパラメーターとして指定できます。これは、シミュレートしようとしていたものです。

Dictionary<String, String> myDictionary = new Dictionary<String, String>();
Type[] arguments = myDictionary.GetType().GetGenericArguments();

Type dictToCreate = typeof(Dictionary<,>).MakeGenericType(arguments);
var mySecondDictionary = Activator.CreateInstance(dictToCreate);

上記のコードは、辞書がString,String事前にあることを知っているため、本質的に無意味ですが、実行時に必要な型を他の場所で検出する方法があると仮定すると、最後の 2 行を使用してその型の辞書をインスタンス化できます。

于 2013-07-07T18:32:28.117 に答える