我在使用Entity Framework从我的DbContext对象生成的SQL中遇到了很多重复的连接。这是我的基本结构
CatalogTable( CatalogID int主键 )
CategoryTable( CategoryID int PRIMARY KEY, CatalogID int NOT NULL )
DepartmentTable( DepartmentID int PRIMARY KEY, CatalogID int NOT NULL)
产品( CatalogID int NOT NULL, CategoryID int NOT NULL, DepartmentID int NOT NULL )
很简单,产品必须有目录,类别和部门。我已经设置了所有导航属性来反映这一点。是的,“产品”可以通过类别或部门间接与目录相关联。但由于有两种可能的路径,我选择明确指出产品属于目录。
因此问题变成了EF继续加入这些必需的关系,基本上为类别和部门吐出了双连接。
型号:
//catalogs
modelBuilder.Entity<Catalog>().ToTable("Catalog.Catalogs");
modelBuilder.Entity<Catalog>().HasKey(k => k.CatalogID);
//products
modelBuilder.Entity<CatalogItem>().ToTable("Catalog.Products");
modelBuilder.Entity<CatalogItem>().HasKey(k => k.ProductID);
modelBuilder.Entity<CatalogItem>().HasRequired(req => req.CatalogCategory).WithMany().Map(m => m.MapKey("CatalogCategoryID"));
modelBuilder.Entity<CatalogItem>().HasRequired(req => req.CatalogDepartment).WithMany().Map(m => m.MapKey("CatalogDepartmentID"));
modelBuilder.Entity<CatalogItem>().HasRequired(req => req.Catalog).WithMany().Map(m => m.MapKey("CatalogID"));
//departments
modelBuilder.Entity<CatalogDepartment>().ToTable("Catalog.Departments");
modelBuilder.Entity<CatalogDepartment>().HasKey(k => k.CatalogDepartmentID);
modelBuilder.Entity<CatalogDepartment>().HasRequired(req => req.Catalog).WithMany().Map(m => m.MapKey("CatalogID"));
//categories
modelBuilder.Entity<CatalogCategory>().ToTable("Catalog.Categories");
modelBuilder.Entity<CatalogCategory>().HasKey(k => k.CatalogCategoryID);
modelBuilder.Entity<CatalogCategory>().HasRequired(req => req.Catalog).WithMany().Map(m => m.MapKey("CatalogID"));
的LINQ:
var query = Products
.Include(inc=>inc.CatalogCategory)
.Include(inc=>inc.CatalogDepartment)
.Include(inc=>inc.Catalog);
query.ToList();
生成的Sql:
SELECT *
FROM [Catalog].[Products] AS [Extent1]
INNER JOIN [Catalog].[Categories] AS [Extent2] ON [Extent1].[CatalogCategoryID] = [Extent2].[CatalogCategoryID]
LEFT OUTER JOIN [Catalog].[Categories] AS [Extent3] ON [Extent1].[CatalogCategoryID] = [Extent3].[CatalogCategoryID]
LEFT OUTER JOIN [Catalog].[Departments] AS [Extent4] ON [Extent1].[CatalogDepartmentID] = [Extent4].[CatalogDepartmentID]
LEFT OUTER JOIN [Catalog].[Catalogs] AS [Extent5] ON [Extent1].[CatalogID] = [Extent5].[CatalogID]
您可以清楚地看到“类别”被连接两次;一次作为内部联接,一次作为外部联接。
这里的任何想法如何干净(和准确)地建立关系但防止重复绑定?谢谢!