c# - 如何按条件 child 过滤列表 parent

标签 c#

不好意思写错了... 我在 mvc 项目中有以下场景。 我有一个具有列表类型属性的对象,该属性还包含一个列表类型子对象。 如何获取 List1 对象,其中 List2 子对象的 cod = 2 和 List3 子对象的 cod = 9。

   public class List1
    {
        public int cod {get;set;}
        public List<List2> list2 {get;set;}
    }

    public class List2
    {
        public int cod {get; set;}
        public List<List3> list3 {get;set;}

    }

    public class List3
    {
        public int cod {get;set;}
    }

    var list1 = new List1() { cod = 1 };
    list1.list2 = new List<List2>();
    list1.list2.Add(new List2
            {
                cod = 1,
                list3 = new List<List3>(){
                new List3{cod = 1},
                new List3{cod = 2}             
            },

            });

            list1.list2.Add(new List2
            {
                cod = 2,
                list3 = new List<List3>(){
                new List3{cod = 7},
                new List3{cod = 8},
                new List3{cod = 9}
            },

            });
            list1.list2.Add(new List2
            {
                cod = 2,
                list3 = new List<List3>(){
                new List3{cod = 7},            
                new List3{cod = 9},
                new List3{cod = 9}
            },

            });


            listFather.Add(list1);

最佳答案

我认为这个版本会更容易理解:

// How can I get the List1 object,
// where List2 children have cod = 2,
// and List3 children have cod = 9.

var matches = (from l1 in listFather
              from l2 in l1.list2
              from l3 in l2.list3
              where l2.cod == 2 &&
                    l3.cod == 9
              select l1).Distinct();

每当 List1 具有匹配的 List2/List3 组合时,您都会添加相同的 List1 实例,因此最后调用 Distinct() 以便仅列出每个特定实例在您的结果中一次。

这是一个完整的例子:

public class List1
{
    public int cod { get; set; }
    public List<List2> list2 { get; set; }

    public override string ToString()
    {
        StringBuilder sb = new StringBuilder();
        sb.AppendLine("l1-cod: " + cod);
        foreach(List2 l2 in list2)
        {
            sb.AppendLine(l2.ToString());
        }
        return sb.ToString();
    }

}

public class List2
{
    public int cod { get; set; }
    public List<List3> list3 { get; set; }

    public override string ToString()
    {
        StringBuilder sb = new StringBuilder();
        sb.AppendLine("\tl2-cod: " + cod);
        foreach (List3 l3 in list3)
        {
            sb.AppendLine("\t\t" + l3.ToString());
        }
        return sb.ToString();
    }
}

public class List3
{
    public int cod { get; set; }

    public override string ToString()
    {
        return "l3-cod: " + cod;
    }
}

class Program
{

    static void Main(string[] args)
    {
        List<List1> listFather = new List<List1>();

        var listA = new List1() { cod = 1 };
        listA.list2 = new List<List2>();
        listA.list2.Add(new List2
        {
            cod = 1,
            list3 = new List<List3>(){
            new List3{cod = 1},
            new List3{cod = 2}
        },

        });

        listA.list2.Add(new List2
        {
            cod = 2,
            list3 = new List<List3>(){
            new List3{cod = 7},
            new List3{cod = 8},
            new List3{cod = 9}
        },

        });
        listA.list2.Add(new List2
        {
            cod = 2,
            list3 = new List<List3>(){
            new List3{cod = 7},
            new List3{cod = 9},
            new List3{cod = 9}
        },

        });
        listFather.Add(listA);

        var listB = new List1() { cod = 2 };
        listB.list2 = new List<List2>();
        listB.list2.Add(new List2
        {
            cod = 1,
            list3 = new List<List3>(){
            new List3{cod = 1},
            new List3{cod = 2}
        },

        });

        listB.list2.Add(new List2
        {
            cod = 2,
            list3 = new List<List3>(){
            new List3{cod = 7},
            new List3{cod = 8},
            new List3{cod = 10}
        },

        });
        listFather.Add(listB);

        var listC = new List1() { cod = 5 };
        listC.list2 = new List<List2>();
        listC.list2.Add(new List2
        {
            cod = 4,
            list3 = new List<List3>(){
            new List3{cod = 6},
            new List3{cod = 7}
        },

        });

        listC.list2.Add(new List2
        {
            cod = 2,
            list3 = new List<List3>(){
            new List3{cod = 7},
            new List3{cod = 8},
            new List3{cod = 10}
        },

        });
        listFather.Add(listC);

        var listD = new List1() { cod = 7 };
        listD.list2 = new List<List2>();
        listD.list2.Add(new List2
        {
            cod = 8,
            list3 = new List<List3>(){
            new List3{cod = 1},
            new List3{cod = 2}
        },

        });

        listD.list2.Add(new List2
        {
            cod = 2,
            list3 = new List<List3>(){
            new List3{cod = 7},
            new List3{cod = 9},
            new List3{cod = 1}
        },

        });
        listFather.Add(listD);

        Console.WriteLine("All objects:");            
        foreach(List1 l1 in listFather)
        {
            Console.WriteLine(l1);
        }
        Console.WriteLine("----------");

        // How can I get the List1 object,
        // where List2 children have cod = 2,
        // and List3 children have cod = 9.
        var matches = (from l1 in listFather
                      from l2 in l1.list2
                      from l3 in l2.list3
                      where l2.cod == 2 &&
                            l3.cod == 9
                      select l1).Distinct();

        Console.WriteLine("All matches:");
        foreach (List1 l1 in matches)
        {
            Console.WriteLine(l1);
        }
        Console.WriteLine();

        Console.Write("Press Enter to quit");
        Console.ReadLine();
    }

}

输出:

All objects:
l1-cod: 1
        l2-cod: 1
                l3-cod: 1
                l3-cod: 2

        l2-cod: 2
                l3-cod: 7
                l3-cod: 8
                l3-cod: 9

        l2-cod: 2
                l3-cod: 7
                l3-cod: 9
                l3-cod: 9


l1-cod: 2
        l2-cod: 1
                l3-cod: 1
                l3-cod: 2

        l2-cod: 2
                l3-cod: 7
                l3-cod: 8
                l3-cod: 10


l1-cod: 5
        l2-cod: 4
                l3-cod: 6
                l3-cod: 7

        l2-cod: 2
                l3-cod: 7
                l3-cod: 8
                l3-cod: 10


l1-cod: 7
        l2-cod: 8
                l3-cod: 1
                l3-cod: 2

        l2-cod: 2
                l3-cod: 7
                l3-cod: 9
                l3-cod: 1


----------
All matches:
l1-cod: 1
        l2-cod: 1
                l3-cod: 1
                l3-cod: 2

        l2-cod: 2
                l3-cod: 7
                l3-cod: 8
                l3-cod: 9

        l2-cod: 2
                l3-cod: 7
                l3-cod: 9
                l3-cod: 9


l1-cod: 7
        l2-cod: 8
                l3-cod: 1
                l3-cod: 2

        l2-cod: 2
                l3-cod: 7
                l3-cod: 9
                l3-cod: 1



Press Enter to quit

关于c# - 如何按条件 child 过滤列表 parent ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59052237/

相关文章:

C# 舍入 MidpointRounding.ToEven 与 MidpointRounding.AwayFromZero

c# - 在代码优先迁移中向具有现有行的表添加唯一索引时处理重复项

c# - 数据集的插入/删除/修改的正确顺序是什么?

C# LINQ - 从单个元素中检索多个属性,转换为结构化(非 xml)文本

c# - RestSharp:无法创建 SSL/TLS 安全通道

c# - 如何通过 COM 互操作将 VBA 变量数组数据类型传递到 C# 方法中

c# - 如何使用 Roslyn 读取 XML 文档注释

c# - 从作为 Azure Web App 托管的 ASP.NET 5 应用程序进行日志记录

c# - 从 C#.Net 调用 Java 函数

C#:在 C# 4.5 中等待请求完成