1

私は登録されたタイプの辞書を持っています。

Dictionary<Type, Type> knownTypes = new Dictionary<Type, Type>() {
   { typeof(IAccountsPlugin), typeof(DbTypeA) },
   { typeof(IShortcodePlugin), typeof(DbTypeB) }
};

オブジェクトが特定のインターフェイスをキーとして実装しているかどうかをテストする必要があります。実装している場合は、対応する値をインスタンス化します。

public Plugin FindDbPlugin(object pluginOnDisk)
{
    Type found;
    Type current = type.GetType();

    // the below doesn't work - need a routine that matches against a graph of implemented interfaces
    knownTypes.TryGetValue(current, out found); /
    if (found != null)
    {
        return (Plugin)Activator.CreateInstance(found);
    }
}

作成されるすべてのタイプ(この場合はDbTypeA、DbTypeBなど)は、タイプからのみ派生しPluginます。

渡されるオブジェクトは、数世代の継承によって、照合しようとしているタイプの1つ(つまり、IAccountsPlugin)から継承される可能性があります。これが私ができない理由ですpluginOnDisk.GetType()

オブジェクトが型を実装しているかどうかをテストし、長いループでtypeofをブルートフォースしてテストするのではなく、辞書ルックアップを使用してその型の新しいインスタンスを作成する方法はありますか?

4

2 に答える 2

2

このメソッドを汎用に変更し、探しているオブジェクトのタイプを指定します。

public Plugin FindDbPlugin<TKey>(TKey pluginOnDisk)
{
    Type found;
    if (knownTypes.TryGetValue(typeof(TKey), out found) && found != null)
    {
        Plugin value = Activator.CreateInstance(found) as Plugin;
        if (value == null)
        {
            throw new InvalidOperationException("Type is not a Plugin.");
        }

        return value;
    }

    return null;
}

例:

IAccountsPlugin plugin = ...
Plugin locatedPlugin = FindDbPlugin(plugin);
于 2012-09-23T22:35:06.903 に答える
1
public Plugin FindDbPlugin(object pluginOnDisk) {        
    Type found = pluginOnDisk.GetType().GetInterfaces().FirstOrDefault(t => knownTypes.ContainsKey(t));
    if (found != null) {
        return (Plugin) Activator.CreateInstance(knownTypes[found]);
    }
    throw new InvalidOperationException("Type is not a Plugin.");
}
于 2012-09-23T22:53:24.327 に答える