LINQ to SQL:多个连接在多个列上。 这可能吗?

鉴于:

名为TABLE_1的表格,包含以下列:

  • ID
  • ColumnA
  • ColumnB
  • ColumnC

我有SQL查询,其中TABLE_1根据ColumnAColumnBColumnC两次join本身。 查询可能看起来像这样:

 Select t1.ID, t2.ID, t3.ID From TABLE_1 t1 Left Join TABLE_1 t2 On t1.ColumnA = t2.ColumnA And t1.ColumnB = t2.ColumnB And t1.ColumnC = t2.ColumnC Left Join TABLE_1 t3 On t2.ColumnA = t3.ColumnA And t2.ColumnB = t3.ColumnB And t2.ColumnC = t3.ColumnC ... and query continues on etc. 

问题:

我需要在LINQ中重写Query。 我试过了一下:

 var query = from t1 in myTABLE1List // List<TABLE_1> join t2 in myTABLE1List on t1.ColumnA equals t2.ColumnA && t1.ColumnB equals t2.ColumnA // ... and at this point intellisense is making it very obvious // I am doing something wrong :( 

我如何在LINQ中编写我的查询? 我究竟做错了什么?

joinLinq to SQL中的多个列有些不同。

 var query = from t1 in myTABLE1List // List<TABLE_1> join t2 in myTABLE1List on new { t1.ColumnA, t1.ColumnB } equals new { t2.ColumnA, t2.ColumnB } ... 

你必须利用匿名types,并为你想要比较的多个列组成一个types。

这看起来很混乱,但是一旦你熟悉了由expression式组成的SQL的方式,它将会变得更有意义,在封面下,这将产生你正在寻找的联接的types。

编辑添加基于评论的第二个连接的示例。

 var query = from t1 in myTABLE1List // List<TABLE_1> join t2 in myTABLE1List on new { A = t1.ColumnA, B = t1.ColumnB } equals new { A = t2.ColumnA, B = t2.ColumnB } join t3 in myTABLE1List on new { A = t2.ColumnA, B = t2.ColumnB } equals new { A = t3.ColumnA, B = t3.ColumnB } ... 

在LINQ2SQL中,当使用内部连接时,你很less需要显式连接。

如果你的数据库中有适当的外键关系,你将会自动在LINQdevise器中获得一个关系(如果没有的话,你可以在devise器中手动创build一个关系,尽pipe你应该在你的数据库中有真正的关系)

亲子关系

然后你可以用“点符号”来访问相关表格

 var q = from child in context.Childs where child.Parent.col2 == 4 select new { childCol1 = child.col1, parentCol1 = child.Parent.col1, }; 

会生成查询

 SELECT [t0].[col1] AS [childCol1], [t1].[col1] AS [parentCol1] FROM [dbo].[Child] AS [t0] INNER JOIN [dbo].[Parent] AS [t1] ON ([t1].[col1] = [t0].[col1]) AND ([t1].[col2] = [t0].[col2]) WHERE [t1].[col2] = @p0 -- @p0: Input Int (Size = -1; Prec = 0; Scale = 0) [4] -- Context: SqlProvider(Sql2008) Model: AttributedMetaModel Build: 4.0.30319.1 

在我看来,这是更可读的,让你专注于你的特殊条件,而不是join的实际机制。

编辑
这当然只适用于当你想join我们的数据库模型。 如果你想join“模型之外”,你需要像Quintin Robinson的回答那样使用手动连接

Title_Authors是一次查看两件东西join项目结果并继续链接

  DataClasses1DataContext db = new DataClasses1DataContext(); var queryresults = from a in db.Authors join ba in db.Title_Authors on a.Au_ID equals ba.Au_ID into idAuthor from c in idAuthor join t in db.Titles on c.ISBN equals t.ISBN select new { Author = a.Author1,Title= t.Title1 }; foreach (var item in queryresults) { MessageBox.Show(item.Author); MessageBox.Show(item.Title); return; } 

你也可以使用:

 var query = from t1 in myTABLE1List join t2 in myTABLE1List on new { ColA=t1.ColumnA, ColB=t1.ColumnB } equals new { ColA=t2.ColumnA, ColB=t2.ColumnB } join t3 in myTABLE1List on new {ColC=t2.ColumnA, ColD=t2.ColumnB } equals new { ColC=t3.ColumnA, ColD=t3.ColumnB } 

我想给出另一个例子,其中使用了多个(3)连接。

  DataClasses1DataContext ctx = new DataClasses1DataContext(); var Owners = ctx.OwnerMasters; var Category = ctx.CategoryMasters; var Status = ctx.StatusMasters; var Tasks = ctx.TaskMasters; var xyz = from t in Tasks join c in Category on t.TaskCategory equals c.CategoryID join s in Status on t.TaskStatus equals s.StatusID join o in Owners on t.TaskOwner equals o.OwnerID select new { t.TaskID, t.TaskShortDescription, c.CategoryName, s.StatusName, o.OwnerName }; 

如果两个表中的列数不相同,并且可以将静态值映射到表列,也可以join

 from t1 in Table1 join t2 in Table2 on new {X = t1.Column1, Y = 0 } on new {X = t2.Column1, Y = t2.Column2 } select new {t1, t2} 

在我看来,这是连接两个表格与多个领域最简单的方法:

 from a in Table1 join b in Table2 on (a.Field1.ToString() + "&" + a.Field2.ToString()) equals (b.Field1.ToString() + "&" + b.Field2.ToString()) select a 

你可以这样写你的查询。

 var query = from t1 in myTABLE1List // List<TABLE_1> join t2 in myTABLE1List on t1.ColumnA equals t2.ColumnA and t1.ColumnB equals t2.ColumnA 

如果你想比较你的列与多列。