簡體   English   中英

在 C# 中根據參數類型創建不同的通用對象

[英]Create different generic objects based on argument type in C#

假設我有一個包含許多(比如 10 個)類 A1,..., A10 的列表,它們都繼承自基類A並且我有從它們到其他 10 個類 B1,...的一對一映射, B10. 我還有一個通用類MyClass<T>並且我希望有一個函數Func(A a)如果輸入是A1的實例,它會創建一個MyClass<B1>實例,如果輸入是,則創建一個MyClass<B2>實例A2一個實例等。我可以使用 switch 語句來完成,但如果類的數量增加,它會變得混亂。 這樣做的好方法是什么?

這是一個具體的例子:假設 A 類是CatDog ,B 類是FooBar ,我有另一個 Generator 類來生成這些實例。

public class Generator{
    public Foo Generate(Cat c){ 
        // some code
    }
     
    public Bar Generate(Dog d){
        // some code
    }
}

我在下面有一個通用類

public class MyClass<T>{
   private T _t; 

   public MyClass(T t){
       this._t = t; 
   }
}

現在在代碼中我想做這樣的事情

Generator gen = new Generator(); 
dynamic animal = new Dog(); 
var result = gen.Generate(animal); // can be of type Foo or Bar  
var cl = new MyClass(result); // does not compile!

最后一行無法編譯,因為它缺少泛型類型參數。

如果需要更多詳細信息,請告訴我!

每種類型的A都知道如何生產它對應的B嗎? 然后你不必有一個大的決策樹在一些單獨的代碼中測試 A 的類型,然后創建 Bs ......該代碼只需調用 a.GetB()。

請注意,在使用這樣的動態時,很難擺脫在上游使用動態。 要指定泛型參數,一種方法是創建一個可以推斷類型的工廠方法:

namespace ConsoleApp13
{
    public class Program
    {
        public static void Main() {
            Generator gen = new Generator(); 
            dynamic animal = new Dog(); 
            var result = gen.Generate(animal); // can be of type Foo or Bar  
            var myClass = MyClass.Create(result);
        }
    }
    public static class MyClass
    {
        public static MyClass<T> Create<T>(T value) => new MyClass<T>(value);
    }
    public class Generator{
        public Foo Generate(Cat c){ 
            // some code
            return new Foo();
        }
     
        public Bar Generate(Dog d){
            // some code
            return new Bar();
        }
    }
    public class MyClass<T>{
        private T _t; 

        public MyClass(T t){
            this._t = t; 
        }
    }


    public class Dog
    {
    }

    public class Bar
    {
    }

    public class Cat
    {
    }

    public class Foo
    {
    }
}

但正如其他人所說,在這種情況下,如果您讓A類創建B作為動態並且不再需要Generator類,則不需要:

namespace ConsoleApp13
{
    public class Program
    {
        public static void Main() {
            var animal = new Dog();
            var myClassWithoutNewMethod = new MyClass<Bar>(animal.GetBar());
            var myClass = MyClass.Create(animal);
        }
    }
    public static class MyClass
    {
        public static MyClass<T> Create<T>(T value) => new MyClass<T>(value);
    }
    public class MyClass<T>{
        private T _t; 

        public MyClass(T t){
            this._t = t; 
        }
    }


    public class Dog
    {
        public Bar GetBar()
        {
            return new Bar();
        }
    }

    public class Bar
    {
    }

    public class Cat
    {
    }

    public class Foo
    {
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM