抽象クラスの継承クラスをすべて取得する [重複] 質問する

抽象クラスの継承クラスをすべて取得する [重複] 質問する

抽象クラスがあります:

abstract class AbstractDataExport
{
        public string name;
        public abstract bool ExportData();
}

AbstractDataExport から派生したクラスがあります:

class XmlExport : AbstractDataExport
{
    new public string name = "XmlExporter";
    public override bool ExportData()
    {
        ...
    }
}
class CsvExport : AbstractDataExport
{
    new public string name = "CsvExporter";
    public override bool ExportData()
    {
        ...
    }
}

このようなことは可能でしょうか? (疑似コード:)

foreach (Implementation imp in Reflection.GetInheritedClasses(AbstractDataExport)
{
    AbstractDataExport derivedClass = Implementation.CallConstructor();
    Console.WriteLine(derivedClass.name)
}

出力は次のようになります

CsvExporter
XmlExporter

?

この背後にある考え方は、AbstractDataExport から派生した新しいクラスを作成し、すべての実装を自動的に反復処理して、たとえば名前をドロップダウン リストに追加できるようにすることです。プロジェクト内の他の部分を変更せずに派生クラスをコーディングし、再コンパイルするだけで完了です。

代替の解決策がある場合は、それを伝えてください。

ありがとう

ベストアンサー1

これは、特に GUI アプリケーションでは非常に一般的な問題なので、これをすぐに実行できる BCL クラスがないことに驚いています。ここでは、その方法を説明します。

public static class ReflectiveEnumerator
{
    static ReflectiveEnumerator() { }

    public static IEnumerable<T> GetEnumerableOfType<T>(params object[] constructorArgs) where T : class, IComparable<T>
    {
        List<T> objects = new List<T>();
        foreach (Type type in 
            Assembly.GetAssembly(typeof(T)).GetTypes()
            .Where(myType => myType.IsClass && !myType.IsAbstract && myType.IsSubclassOf(typeof(T))))
        {
            objects.Add((T)Activator.CreateInstance(type, constructorArgs));
        }
        objects.Sort();
        return objects;
    }
}

いくつかの注意事項:

  • この操作の「コスト」については心配しないでください。この操作は 1 回だけ実行され (うまくいけば)、その場合でも思ったほど遅くはありません。
  • Assembly.GetAssembly(typeof(T))基本クラスが別のアセンブリにある可能性があるため、を使用する必要があります。
  • インターフェースまたは抽象クラスをインスタンス化しようとすると例外がスローされるため、type.IsClass基準を使用する必要があります。!type.IsAbstract
  • IComparable列挙されたクラスを強制的に実装して、ソートできるようにするのが好きです。
  • 子クラスには同一のコンストラクター シグネチャが必要です。そうでない場合は例外がスローされます。これは通常、私にとっては問題ではありません。

おすすめ記事