在列表中循环<;界面>;项目

本文关键字:界面 gt 项目 列表 lt 循环 | 更新日期: 2023-09-27 18:01:08

我不明白为什么我不能通过我接口的类迭代列表。

例如。

public interface IAnimal
{
   string Name { get; set; }
}
public class Chicken:IAnimal
{
   public string Name { get; set; }
}
public class Dog:IAnimal
{
   public string Name { get; set; }
}
class Program
{
    static void Main(string[] args)
    {
        var AnimalList = new List<IAnimal>();
        var Chicken1= new Chicken() { Name = "Chicken" }; 
        var Dog1= new Dog() { Name = "Dog" };
        AnimalList.Add(Dog1);
        AnimalList.Add(Chicken1);
        foreach (Dog obj in AnimalList)
        {
           Console.WriteLine(obj.Name); 
        }
    }
}

我做错了什么吗,有没有更好的角度来处理这种情况。

在列表中循环<;界面>;项目

您已经定义了您的列表,使其包含IAnimal的元素。

var AnimalList = new List<IAnimal>();

然后在循环中,将元素指定为Dog。虽然Dog确实实现了IAnimal,但它并不是唯一实现的类型。因此,如果列表包含Dog以外的类型,则循环失败。

所以你有两种方法来解决这个问题。

一个是你把你的循环改成这样:

foreach (IAnimal obj in AnimalList)
{
    Console.WriteLine(obj.Name); 
}

如果你这样做,你的代码运行良好,并输出狗和鸡的名字。

但是,如果您只希望返回Dog实例,则可以筛选列表。你可以这样做:

foreach (Dog obj in AnimalList.OfType<Dog>())
{
    Console.WriteLine(obj.Name); 
}

现在它只输出狗的名字。

每个Dog都是IAnimal,但不是每个IAnimalDog。尤其不是Chicken:它绝对不是Dog。这就是为什么当这个循环到达Chicken:时会遇到异常的原因

foreach (Dog obj in AnimalList) {
    ...
}

然而,如果你像这个那样做

foreach (IAnimal obj in AnimalList) {
    ...
}

或等效

foreach (var obj in AnimalList) {
    ...
}

代码将正确编译和运行。