Linq在多个层上排序IEnumerable

Atr*_*ige 3 c# linq sorting entity-framework

我正在编写一个简单的测试应用程序来展示如何对我将从EF上下文中获取的列表进行排序.

"目标"是获取一个列表,按Student.Name排序,然后按Subject.Name排序

public class Student
{
    public string Name {get;set;}
    public List<ExamScore> ExamScores{get;set;}
}

public class Subject
{
    public string Name{get;set;}
}

public class ExamScore
{
    public Subject Subject{get;set;}
    public int Score{get;set;}
}
Run Code Online (Sandbox Code Playgroud)

第一级排序很简单:

var list = con.Students
    .Include(e => e.ExamScores
        .Select(s => s.Subjects))
    .OrderBy(x => x.Name) //student.Name
    .ToList();
Run Code Online (Sandbox Code Playgroud)

但是添加下一个级别让我感到困惑.

var list = con.Students
    .Include(e => e.ExamScores
        .Select(s => s.Subjects))
    .OrderBy(x => x.Name) //student.Name
    .ThenBy(y => y.ExamScores.???) //subject name???
    .ToList();
Run Code Online (Sandbox Code Playgroud)

输入

Student{"Jannie", ExamScore{ Subject{"Math"}, 90}}
Student{"Jannie", ExamScore{ Subject{"History"}, 70}}
Student{"Jannie", ExamScore{ Subject{"Science"}, 90}}

Student{"Koos", ExamScore{ Subject{"Xhosa"}, 83}}
Student{"Koos", ExamScore{ Subject{"Afrikaans"}, 74}}
Student{"Koos", ExamScore{ Subject{"English"}, 78}}

Student{"Pieter", ExamScore{ Subject{"Afrikaans"}, 65}}
Student{"Pieter", ExamScore{ Subject{"History"}, 80}}
Student{"Pieter", ExamScore{ Subject{"Math"}, 70}}

Student{"Sannie", ExamScore{ Subject{"Science"}, 60}}
Student{"Sannie", ExamScore{ Subject{"Math"}, 55}}
Student{"Sannie", ExamScore{ Subject{"Biology"}, 75}}

Student{"Magriet", ExamScore{ Subject{"Biology"}, 75}}
Student{"Magriet", ExamScore{ Subject{"English"}, 80}}
Student{"Magriet", ExamScore{ Subject{"Science"}, 90}}
Run Code Online (Sandbox Code Playgroud)

预期产出

Student{"Jannie", ExamScore{ Subject{"History"}, 70}}
Student{"Jannie", ExamScore{ Subject{"Math"}, 90}}
Student{"Jannie", ExamScore{ Subject{"Science"}, 90}}

Student{"Koos", ExamScore{ Subject{"Afrikaans"}, 74}}
Student{"Koos", ExamScore{ Subject{"English"}, 78}}
Student{"Koos", ExamScore{ Subject{"Xhosa"}, 83}}

Student{"Magriet", ExamScore{ Subject{"Biology"}, 75}}
Student{"Magriet", ExamScore{ Subject{"English"}, 80}}
Student{"Magriet", ExamScore{ Subject{"Science"}, 90}}

Student{"Pieter", ExamScore{ Subject{"Afrikaans"}, 65}}
Student{"Pieter", ExamScore{ Subject{"History"}, 80}}
Student{"Pieter", ExamScore{ Subject{"Math"}, 70}}

Student{"Sannie", ExamScore{ Subject{"Biology"}, 75}}
Student{"Sannie", ExamScore{ Subject{"Math"}, 55}}
Student{"Sannie", ExamScore{ Subject{"Science"}, 60}}
Run Code Online (Sandbox Code Playgroud)

Dmi*_*mov 7

您需要做的是首先展开学生 - >主题关系,然后您将能够对两者进行排序:

var list = con.Students.Include(e => e.ExamScores.Select(s => s.Subjects))
    .SelectMany(student => student.ExamScores.Select(score => new { Student = student, Score = score }))
    .OrderBy(x => x.Student.Name)
    .ThenBy(x => x.Score.Subject.Name);
Run Code Online (Sandbox Code Playgroud)

这将生成一个可枚举的匿名对象,其中包含按学生姓名和科目名称排序的学生和分数.