C# 设计模式:对象列表的多态性

C# 设计模式:对象列表的多态性,c#,java,design-patterns,C#,Java,Design Patterns,假设我有一个类a,A1,A2继承自a。 有两个功能: List<A1> getListA1(){...} List<A2> getListA2(){...} List getListA1(){…} 列表getListA2(){…} 现在我想在另一个函数中做一些类似于A1和A2的事情 public void process(List<A>){...} 公共作废流程(列表){…} 如果我想传递ListA1或ListA2的实例,类型当然不匹配,因为编译器不允

假设我有一个类a,A1,A2继承自a。 有两个功能:

List<A1> getListA1(){...}
List<A2> getListA2(){...}
List getListA1(){…}
列表getListA2(){…}
现在我想在另一个函数中做一些类似于A1和A2的事情

public void process(List<A>){...}
公共作废流程(列表){…}
如果我想传递ListA1或ListA2的实例,类型当然不匹配,因为编译器不允许从List强制到List。我不能这样做:

List<A1> listA1 = getListA1();
List<A> newList = (List<A>)listA1; //this is not allowed.
List listA1=getListA1();
List newList=(List)listA1//这是不允许的。
那么,处理流程()的最佳方法是什么?有没有什么方法可以以通用的方式来执行此操作,而不是将类似的代码写入列表和列表?

使用通配符绑定:

public void process(List<? extends A>){...}
public void进程(List使用IEnumerable中的扩展方法。

不能
getListA1()
getListA2()
只在第一个实例中返回列表类型

List<A> getListA1(){...}
List<A> getListA2(){...}
List getListA1(){…}
列表getListA2(){…}

虽然我不能提供java解决方案,但这里有一些C#

如果您可以更改进程的签名以接受IEnumerable

public void Process(IEnumerable<A> myList) { ... }
import java.util.*;
甲级{
int x;
}
A1类扩展了A类{
int-y;
}
A2类扩展了A类{
intz;
}
公共类多态性ForListofObject{
静态void foo(List尝试以下示例:



using System.Collections.Generic;

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            List myList;

            myList = GetMyList(MyListTypeEnum.MyList1);
            myList = GetMyList(MyListTypeEnum.MyList2);
        }

        public static List GetMyList(MyListTypeEnum tipo)
        {
            List result;
            result = new List();

            switch (tipo)
            {
                case MyListTypeEnum.MyList1:
                    List myList1 = GetMyList1();
                    foreach (var item in myList1)
                    {
                        result.Add((IMyList) item);
                    }
                    break;
                case MyListTypeEnum.MyList2:
                    List myList2 = GetMyList2();
                    foreach (var item in myList2)
                    {
                        result.Add((IMyList) item);
                    }
                    break;
            }

            return result;
        }

        public static List GetMyList1()
        {
            List myList1 = new List();
            myList1.Add(new MyList1 { Code = 1 });
            myList1.Add(new MyList1 { Code = 2 });
            myList1.Add(new MyList1 { Code = 3 });
            return myList1;
        }

        public static List GetMyList2()
        {
            List myList2 = new List();
            myList2.Add(new MyList2 { Name = "1" });
            myList2.Add(new MyList2 { Name = "2" });
            myList2.Add(new MyList2 { Name = "3" });
            return myList2;
        }
    }

    public interface IMyList
    {
    }

    public class MyList1 : IMyList
    {
        public int Code { get; set; }
    }

    public class MyList2 : IMyList
    {
        public string Name { get; set; }
    }

    public enum MyListTypeEnum
    {
        MyList1,
        MyList2
    }
}


我以前考虑过这一点。问题是这两种方法在其他地方使用,我已经改变了所有相关的地方。
public void Process(List<A> myList) { ... }

var someList = getListA1();
Process( someList.Cast<A>());
import java.util.*;

class A {
    int x;
}

class A1 extends A {
    int y;
}

class A2 extends A {
    int z;
}

public class polymorphisimForListOfObjects {
    static void foo(List<? extends A> l) { // probably can't modify the list
        System.out.println(l);
    }

    public static void main(String[] arguments) {
        A1[] a1 = { new A1(), new A1() };
        A2[] a2 = { new A2(), new A2() };
        List<A1> l1 = Arrays.asList(a1);
        List<A2> l2 = Arrays.asList(a2);
        foo(l1);
        foo(l2);
    }

}


using System.Collections.Generic;

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            List myList;

            myList = GetMyList(MyListTypeEnum.MyList1);
            myList = GetMyList(MyListTypeEnum.MyList2);
        }

        public static List GetMyList(MyListTypeEnum tipo)
        {
            List result;
            result = new List();

            switch (tipo)
            {
                case MyListTypeEnum.MyList1:
                    List myList1 = GetMyList1();
                    foreach (var item in myList1)
                    {
                        result.Add((IMyList) item);
                    }
                    break;
                case MyListTypeEnum.MyList2:
                    List myList2 = GetMyList2();
                    foreach (var item in myList2)
                    {
                        result.Add((IMyList) item);
                    }
                    break;
            }

            return result;
        }

        public static List GetMyList1()
        {
            List myList1 = new List();
            myList1.Add(new MyList1 { Code = 1 });
            myList1.Add(new MyList1 { Code = 2 });
            myList1.Add(new MyList1 { Code = 3 });
            return myList1;
        }

        public static List GetMyList2()
        {
            List myList2 = new List();
            myList2.Add(new MyList2 { Name = "1" });
            myList2.Add(new MyList2 { Name = "2" });
            myList2.Add(new MyList2 { Name = "3" });
            return myList2;
        }
    }

    public interface IMyList
    {
    }

    public class MyList1 : IMyList
    {
        public int Code { get; set; }
    }

    public class MyList2 : IMyList
    {
        public string Name { get; set; }
    }

    public enum MyListTypeEnum
    {
        MyList1,
        MyList2
    }
}