首先将您的逻辑分解为单独的操作,而不是尝试将所有内容写在一行中。编译器是智能 cookie,因此它们可以很好地优化事物,没有必要让您的代码更难阅读/理解:
var facultySpecialties = specialty.faculty_specialties
.Where(fs => fs.faculty.active)
.ToList(); // Executes the query to retrieve faculty specialties.
foreach(var facultySpecialty in facultySpecialties)
{
// do stuff.
}
请注意您在查询中引用的实体的范围。上面的查询将返回faculty_specialties,而不是faculties。需要注意的一个问题:由于这会返回 fac_specs,如果您想在 foreach 循环中访问 fac_spec 和教员的详细信息,那么也包括教员。
var facultySpecialties = specialty.faculty_specialties
.Include(fs => fs.faculty)
.Where(fs => fs.faculty.active)
.ToList();
如果您只想要院系,而不需要来自 fac_spec 的信息:
var faculties = specialty.faculty_specialties
.Select(fs => fs.faculty)
.Where(f => f.active)
.ToList();
这会从我们的 fac_specs 中选择教员。请注意 Where 子句发生了变化,因为 .Select() 之后的范围变为 Faculties 而不是 Faculty_Specialities。如果您仍需要 fac_specs 中的详细信息,可以使用 .Include(f => f.faculty_specialties),但如果不需要它们,请不要包含关系,因为这会增加查询的性能成本和传输成本(大小)。
现在您想要订购学院。问题是优先权适用于哪个实体?如果 Priority 是 Faculty 中的一个字段,则:
var faculties = specialty.faculty_specialties
.Select(fs => fs.faculty)
.Where(f => f.active)
.OrderBy(f => f.Priority)
.ToList();
但是,我怀疑优先考虑的是系专业。
如果您有从学院返回到学院专业的导航属性(我假设是多对多关系,因此学院可以映射 ICollection<faculty_specialities>)并且学院在您的上下文中是一个 DbSet,您可能想要重组查询,因为这将使订购更容易:
var faculties = dbContext.Faculties
.Where(f => f.active && f.faculty_specialties.Any(fs => fs.specialty.specialtyId == specialty.specialtyId))
.ToList();
在faculty_speciality.priority上执行命令:
var faculties = dbContext.Faculties
.Where(f => f.active
&& f.faculty_specialties.Any(fs => fs.specialty.specialtyId == specialty.specialtyId))
.OrderByDescending(f => f.faculty_specialties.Min(fs => fs.priority))
.ToList();
您可以尝试对原始查询进行排序,例如:
var faculties = specialty.faculty_specialties
.OrderBy(fs => fs.priority)
.Select(fs => fs.faculty)
.Where(f => f.active)
.ToList();
但是我不确定这种排序是否会在最终结果集中得到体现。
对此类查询要考虑的最后一件事是,随着系统的增长,数据量可能会使此类操作变得非常昂贵,因为给定专业的设施数量会增加。您应该在使用 .Take() 和 .Skip() 的早期考虑对结果大小和分页支持施加限制,除非系统大小的上限被限制在一个合理的数字上。