如何合并通用列表及其属性

时间:2014-12-11 08:13:19

标签: c# generics

我有2个相同类型的通用列表" Person" 每个列表都有" Order"属性。
人员ID(标识符)可以在展位列表中重复。但订单不能。
我想要的输出应该是1个列表,当每个人有一个实例时 并且所有订单都合并了 我的问题是,这样做的最佳方式(性能)是什么? 如下一段代码所述:

class Program
{

    public class Order
    {
        public string OrderId { get; set; }
    }

    public class Person
    {
        public string Id { get; set; }
        public List<Order> orders { get; set; }
    }

    static void Main(string[] args)
    {

        // build list 1
        Person p1 = new Person() { Id = "John", orders = new List<Order>() };
        p1.orders.Add(new Order() { OrderId = "John order 1" });

        Person p2 = new Person() { Id = "Paul", orders = new List<Order>() };
        p2.orders.Add(new Order() { OrderId = "Paul order 1" });

        List<Person> L1 = new List<Person>();
        L1.Add(p1);
        L1.Add(p2);


        // build list 2
        Person p3 = new Person() { Id = "John", orders = new List<Order>() };
        p3.orders.Add(new Order() { OrderId = "John order 2" });

        List<Person> L2 = new List<Person>();
        L2.Add(p3);

        //output 
        List<Person> merged = new List<Person>();

        merged = L1.Union(L2, new PersonComparer()).ToList();


        foreach (var item in merged)
        {
            Console.WriteLine("Person ID: {0}", item.Id);
            foreach (var order in item.orders)
            {
                Console.WriteLine(" --  {0}", order.OrderId);
            }
            Console.WriteLine("-----------------");
        }

        Console.ReadKey();

    }

}

输出:

        /************************************************************
         * current output:
         *
         * Presone ID: John
         * ---  John order 1
         * -------------------------
         * Presone ID: Paul
         * ---  Paul order 1
         * ------------------------ 
         * Presone ID: John
         * ---  John order 2 
         * 
         * 
         * desired output:
         * 
         * Presone ID: John
         * ---  John order 1
         * ---  John order 2 
         * -------------------------
         * Presone ID: Paul
         * ---  Paul order 1
         * ------------------------  
         *    

1 个答案:

答案 0 :(得分:2)

Concat列表,按PersonId分组,然后为每个组创建一个人并连接订单:

L1.Concat(L2)
 .GroupBy(x => x.Id)
 .Select(x => new Person 
              { 
                  Id = x.Key,
                  Orders = x.SelectMany(g => g.Orders).ToList()
              }).ToList();

你在这里不需要Union因为你不想删除重复项。即使你的比较器工作,也会删除重复的人,你将失去{{1}你需要按照他们的ID分组的所有Orders。然后,一旦你获得了这些组,你就可以轻松地将组中所有人的命令输入一个列表。