我有以下疑问:
var query = from customer in _unitOfWork.customerRepository.All()
join adresses in _unitOfWork.AdresRepository.All() on customer.adressNo equals adresses.adressNo into adr
from adresses in adr.DefaultIfEmpty()
select new CustomerResponse
{
CustomerName = customer.Name
Select new Address
{
adressName = adr.name
adressNo = adr.Number
}
}
每个地址的
CustomerResponse
都是重复的。我想要的是一个具有多个地址作为子对象的CustomerResponse
。
EF 已经提供了存储库 (
DBSet
) 和 UoW (DbContext
)。如果您自己的存储库模式正在返回 IQueryable<TEntity>
并且您正在像您应该的那样利用导航属性(首先使用 ORM 的全部意义),那么:
var results = await _unitOfWork.customerRepository.All()
.Select(c => new CustomerResponse
{
CustomerName = c.Name
Addresses = c.Addresses.Select(a => new AddressResponse
{
AddressName = a.Name
AddressNo = a.Number
}).ToList();
}).ToListAsync();
您可以使用 Linq
from
/select
语法执行相同操作,这取决于个人喜好。但我不建议使用 EF + Linq 作为用 C# 编写 SQL 的直接替代品,尤其是在 EF 的 DbSet
之上添加额外的抽象。这完全违背了使用实体框架的目的。在极少数情况下,您需要在 EF 中使用显式 Join
,并且这些情况下表之间没有直接的 FK 关系。在存在 FK 的所有正常情况下,您应该使用导航属性(一对一、一对多、多对多等)并让 EF 管理联接。这就是 EF 的构建目的。
您需要对每个客户的地址进行分组,以便您可以为每个客户返回一个 CustomerResponse,并将一组地址作为子对象。您可以通过姓名来了解客户,然后将地址组合到其中
var query = from customer in _unitOfWork.customerRepository.All()
join address in _unitOfWork.AdresRepository.All() on customer.adressNo equals address.adressNo into adr
from address in adr.DefaultIfEmpty()
group address by new { customer.Name} into grouped
select new CustomerResponse
{
CustomerName = grouped.Key.Name,
Addresses = grouped
.Where(a => a != null)
.Select(a => new Address
{
adressName = a.name,
adressNo = a.Number
})
.ToList()
};