将IEnumerable <T>转换为IEnumerable <U>?

Rip*_*ppo 12 c# ienumerable casting

以下符合但在运行时抛出异常.我想要做的是将类PersonWithAge强制转换为Person类.我该怎么做,有什么工作?

class Person
{
    public int Id { get; set; }
    public string Name { get; set; }
}

class PersonWithAge
{
    public int Id { get; set; }
    public string Name { get; set; }
    public int Age { get; set; }
}

class Program
{
    static void Main(string[] args)
    {
        IEnumerable<PersonWithAge> pwa = new List<PersonWithAge>
        {
            new PersonWithAge {Id = 1, Name = "name1", Age = 23},
            new PersonWithAge {Id = 2, Name = "name2", Age = 32}
        };

        IEnumerable<Person> p = pwa.Cast<Person>();

        foreach (var i in p)
        {
            Console.WriteLine(i.Name);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

编辑:顺便说一句,PersonWithAge将始终包含与Person相同的属性以及更多.

编辑2对不起家伙,但我应该更清楚一点,说我在包含相同列的数据库中有两个数据库视图,但视图2包含1个额外字段.我的模型视图实体由模仿数据库视图的工具生成.我有一个MVC局部视图,它继承自一个类实体,但我有多种方法来获取数据...

不确定这是否有帮助,但这意味着我不能让人与人继承.

Mar*_*ers 18

你不能投,因为他们是不同的类型.你有两个选择:

1)更改类,以便PersonWithAge继承自person.

class PersonWithAge : Person
{
        public int Age { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

2)创建新对象:

IEnumerable<Person> p = pwa.Select(p => new Person { Id = p.Id, Name = p.Name });
Run Code Online (Sandbox Code Playgroud)


Dar*_*rov 8

使用Select而不是Cast来指示如何执行从一种类型到另一种类型的转换:

IEnumerable<Person> p = pwa.Select(x => new Person { Id = x.Id, Name = x.Name });
Run Code Online (Sandbox Code Playgroud)

另外,因为它PersonWithAge总是包含相同的属性,Person再加上几个,它会更好地继承它Person.


Jor*_*ren 5

你不能只是将两个不相关的类型相互转换。您可以通过让 PersonWithAge 从 Person 继承来将 PersonWithAge 转换为 Person。由于 PersonWithAge 显然是 Person 的一个特例,所以这很有意义:

class Person
{
        public int Id { get; set; }
        public string Name { get; set; }
}

class PersonWithAge : Person
{
        // Id and Name are inherited from Person

        public int Age { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

现在,如果您有一个IEnumerable<PersonWithAge>named personsWithAge,那么personsWithAge.Cast<Person>()将起作用。

在 VS 2010 中,您甚至可以完全跳过强制转换并执行(IEnumerable<Person>)personsWithAge,因为IEnumerable<T>在 .NET 4 中是协变的。