LINQ包含和继承

时间:2019-07-17 13:46:35

标签: c# .net linq

我有一个使用数据库优先模型的WEB API项目。 我有基类Building实体和MultiApartmentBuilding实体,它们是从Building继承的。我还有一个Apartment实体,它与Building实体以一对多的关系连接。我想通过给定的公寓ID获取特定的公寓,并提供一些MultiApartmentBuilding信息。

到目前为止,我已经尝试通过Include() LINQ方法获得理想的结果,但是遇到一个我不能包含MultiapartmentBuilding的问题。

这是我的Building班。

public abstract class Building
{
    public int Id { get; set; }
    public BuildingState State { get; set; }
    public BuildingType Type { get; set; }
    public int AddressId { get; set; }
    public Address Address { get; set; }
    public MultilingualString Description { get; set; }
    public string MainImg { get; set; }
    public bool IsBuilt { get; set; }
}

这是我的MultiApartmentBuilding班。

public class MultiApartmentBuilding : Building
{
    public int GroundFloorCount { get; set; }
    public double FloorHeight { get; set; }
    public int? WallId { get; set; }
    public Wall Wall { get; set; }       
}

这是我的Apartment班。

public class Apartment : EntityBase
{
    public int Id { get; set; }

    public int BuildingId { get; set; }
    public Building Building { get; set; }
    public Common.Enums.ApartmentState State { get; set; }
    public AccessibilityState Accessibility { get; set; }
    public int Floor { get; set; }
    public bool IsPentHouse { get; set; }
}

这是我的LINQ查询,应该返回单元。

var apartment = _context.Apartments
    .Where(id => id.Id == apartmentId)
    .Include(building => building.Building)
        .ThenInclude(address => address.Address)
        .ThenInclude(city => city.City)
        .ThenInclude(cityName => cityName.Name)
   .Include(district => district.Building.Address.District)
        .ThenInclude(districtName => districtName.Name)
   .Include(street => street.Building.Address.Street)
   .Include(condPrices => condPrices.ConditionPrices)
        .ThenInclude(condition => condition.Condition)
        .ThenInclude(conditionName => conditionName.Name)
        .ThenInclude(conditionNameTranslation => conditionNameTranslation.Translations)
   .Include(builder => builder.Building.Builder)
        .ThenInclude(brandName => brandName.BrandName)
        .ThenInclude(brandNameTrans => brandNameTrans.Translations)
    .Include(builderBussinesAddress => builderBussinesAddress.Building.Builder.BusinessAddress)
         .ThenInclude(tranlsations => tranlsations.Translations)
   .Include(descriptipon => descriptipon.Description)
        .ThenInclude(descriptionName => descriptionName.Translations)

此查询的问题是我无法访问MultiApartmentBuilding字段。尽管Building是从MultiApartmentBuilding继承的,但是我只能访问Building字段。有没有办法也可以访问MultiApartmenBuilding字段?

3 个答案:

答案 0 :(得分:1)

包含Building还将包括MultiApartmentBuilding个条目(实际上,所有类型都源自Building)。

您可以使用C#7.0的模式匹配来同时测试和投射(其中apartments是查询的结果):

foreach (Apartment apartment in apartments) {
    // Access common Building field.
    Console.WriteLine(apartment.Building.Id);

    // Access specialized field from derived building type.
    if (apartment.Building is MultiApartmentBuilding maBuilding) {
        Console.WriteLine(maBuilding.GroundFloorCount);
    }
}

如果建筑物类型很多,则可以在switch语句中使用模式匹配

switch (apartment.Building)
{
    case MultiApartmentBuilding maBuilding:
        Console.WriteLine(maBuilding.GroundFloorCount);
        break;
    case Igloo igloo:
        Console.WriteLine(igloo.SnowQuality);
        break;
    default:
        Console.WriteLine("all other building types");
        break;
}

答案 1 :(得分:0)

您尝试过投射吗?

var multiApartments = (MultiApartmentBuilding)apartment.Building;

答案 2 :(得分:0)

您无法访问孩子的班级属性。换句话说,如果您拥有建筑物,则无法访问其 MultiApartmentBuilding 属性,因为您甚至不知道它是否真的是 MultiApartmentBuilding 。 在这种情况下,我要做的就是更改您的 Apartment 类,并使用 MultiApartmentBuilding 类型而不是 Building

public class Apartment : EntityBase
{
    public int Id { get; set; }

    public int BuildingId { get; set; }
    public MultiApartmentBuilding MultiApartmentBuilding { get; set; }
    public Common.Enums.ApartmentState State { get; set; }
    public AccessibilityState Accessibility { get; set; }
    public int Floor { get; set; }
    public bool IsPentHouse { get; set; }
 }
相关问题