【问题标题】:LINQ self refenced table filter relationLINQ 自引用表过滤器关系
【发布时间】:2014-10-23 23:37:13
【问题描述】:

我有 2 个表 CategoriesImages 类别是自引用的 ParentId 作为 Nullable Foreign Key

代码优先类

public class Category {

    public int Id { get; set; }
    public string Name{ get; set; }
    public int? ParentId { get; set; }
    public bool IsDeleted { get; set; }
    public byte[] Timestamp { get; set; }

    public virtual Category Parent { get; set; }
    public virtual ICollection<Category> Parents { get; set; }

    public virtual ICollection<Image> Images { get; set; }
}


Public class Image {

    public int Id { get; set; }
    public int? CategoryId { get; set; }
    public string Source { get; set; }
    public string Description { get; set; }
    public bool IsDeleted { get; set; }
    public byte[] Timestamp { get; set; }

    // Foreign keys
    public virtual Category Category { get; set; }
}


public class CategoryMap : EntityTypeConfiguration<Category> {
    public CategoryMap() {
        // Primary Key
        HasKey(t => t.Id);

        // Properties
        Property(t => t.Name).IsRequired().HasMaxLength(250);
        Property(t => t.Timestamp).IsRequired().IsFixedLength().HasMaxLength(8).IsRowVersion();

        // Table & Column Mappings
        ToTable("Category");
        Property(t => t.Id).HasColumnName("Id");
        Property(t => t.ParentId).HasColumnName("ParentId");
        Property(t => t.Name).HasColumnName("Category");
        Property(t => t.IsDeleted).HasColumnName("IsDeleted");
        Property(t => t.Timestamp).HasColumnName("Timestamp");

        // Relationships
        HasOptional(t => t.Parent).WithMany(t => t.Parents)
                                  .HasForeignKey(d => d.ParentId)
                                  .WillCascadeOnDelete(false);
}

public class ProfileImageMap : EntityTypeConfiguration<ProfileImage> {

    public ProfileImageMap() {
        // Primary Key
        HasKey(t => t.Id);

        // Properties
        Property(t => t.Source).IsRequired().HasMaxLength(255);
        Property(t => t.Description).HasMaxLength(255);
        Property(t => t.Timestamp).IsRequired().IsFixedLength().HasMaxLength(8).IsRowVersion();

        // Table & Column Mappings
        ToTable("Images");
        Property(t => t.Id).HasColumnName("Id");
        Property(t => t.CategoryId ).HasColumnName("CategoryId ");
        Property(t => t.Source).HasColumnName("Source");
        Property(t => t.Description).HasColumnName("Description");
        Property(t => t.IsDeleted).HasColumnName("IsDeleted");
        Property(t => t.Timestamp).HasColumnName("Timestamp");

        // Relationships
        HasOptional(t => t.Category).WithMany(t => t.Images)
                                    .HasForeignKey(d => d.CategoryId);
    }
}

** 上下文**

    public DbSet<Category> Categories { get; set; }
    public DbSet<Image> Images { get; set; }

问题是我如何构建一个 LINQ 语句以返回一个基于 Id 的类别与父类别的所有图像,不包括标记为 IsDeleted = true 的图像

是否可以在LINQLinqKit 中做到这一点

【问题讨论】:

  • 你试过了吗?
  • 是的,我尝试了 LinqLinqKit,但我无法过滤图像我认为在 SQL Server 中创建 Stored Procuder 会更容易

标签: c# sql-server linq ef-code-first linqkit


【解决方案1】:

这将为您返回应用过滤器所需的所有详细信息。唯一“复杂”的部分是应用于 Images 属性的 Where 子句(我还添加了空检查,否则您可能会得到 NullReferenceException):

var categoryID = 2; //The ID you are searching for

var category = from c in categories
               where c.Id == categoryID 
               select new Category
               {
                   Id = c.Id,
                   Name = c.Name,
                   ParentId = c.ParentId,
                   IsDeleted = c.IsDeleted,
                   Timestamp = c.Timestamp,
                   Parent = c.Parent,
                   Images = c.Images == null ? 
                       (ICollection<Image>)new List<Image>() : 
                       (ICollection<Image>)c.Images.Where(i => i.IsDeleted = false).ToList()
               }.Single();

如果要返回所有父类别(即遍历层次结构),那么一种方法是拥有这样的函数:

public IEnumerable<Category> GetParents(IEnumerable<Category> categories, Category child) 
{
    List<Category> parents = new List<Category>();
    var current = child.Parent;
    while (current != null)
    {
        parents.Add(parent);
        parent = parent.Parent;
    } 

    return parents;

}

现在你可以说:

category.Parents = GetParents(categories, category);

【讨论】:

  • 感谢 David,它只适用于第一级,我希望它也能过滤所有专利
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-08-02
  • 2011-09-13
  • 1970-01-01
  • 1970-01-01
  • 2019-01-19
相关资源
最近更新 更多