EF多对多关联查询:如何仅获取教师及对应学生姓名?
EF Core 多对多关系:高效查询教师及对应学生姓名列表
实体类定义
public class Teacher { Guid ID; string Name; string Address; string Tel; ICollection<Student> Students; } public class Student { Guid id; string Name; string Address; string Tel; ICollection<Teacher> Teachers; }
这是EF Core自动生成中间表TeacherStudent的多对多关系,需求是查询所有教师,并按以下格式输出每位教师对应的学生姓名(仅保留姓名字段):
Teacher1 name: Student1 name, Student3 name, Student5 name, Student9 name Teacher2 name: Student1 name, Student2 name, Student3 name, Student9 name
遇到的问题
尝试过以下代码:
_context.Teacher.Include(x=>x.TeacherStudent).ThenInclude(y=>y.Student);
虽然能获取教师关联的学生列表,但会加载学生的全部字段(Address、Tel等冗余数据);使用SelectMany则会将数据扁平化,导致教师姓名重复出现。
解决方案
通过投影查询直接只获取需要的字段,避免冗余数据,同时保持教师与学生的层级关系,有两种常见实现方式:
方式1:投影到匿名类型
适合临时查询场景,无需额外定义类:
var teacherStudentNames = _context.Teacher .Select(t => new { TeacherName = t.Name, StudentNames = t.Students.Select(s => s.Name).ToList() }) .ToList();
方式2:投影到自定义DTO类
如果需要在多个业务场景复用数据结构,先定义DTO:
public class TeacherStudentNameDto { public string TeacherName { get; set; } public List<string> StudentNames { get; set; } }
再执行查询:
var teacherStudentNames = _context.Teacher .Select(t => new TeacherStudentNameDto { TeacherName = t.Name, StudentNames = t.Students.Select(s => s.Name).ToList() }) .ToList();
格式化输出示例
拿到数据后,按需求格式输出:
foreach (var item in teacherStudentNames) { Console.WriteLine($"{item.TeacherName}:"); foreach (var studentName in item.StudentNames) { Console.WriteLine($" {studentName},"); } Console.WriteLine(); // 换行分隔不同教师 }
内容的提问来源于stack exchange,提问作者EBDS
相关产品推荐
相关产品推荐

