欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

使用Linq实现SQL的全连接

程序员文章站 2022-07-04 10:20:24
...

在*上看到关于这个问题的讨论,打算记录下来。

关于全连接(Full Outer Join),Linq并不支持,所以就需要使用其它方法来实现,就像不支持全连接的数据库一样,先使用内连接找出公共的部分,然后分别找出左连接和右连接的部分,把这三部分的结果UNION一下,即可得到全连接的效果。

看问题:

ID  FirstName
--  ---------
 1  John
 2  Sue

ID  LastName
--  --------
 1  Doe
 3  Smith
显示下面的结果:
ID  FirstName  LastName
--  ---------  --------
 1  John       Doe
 2  Sue
 3             Smith

 

实现方法一:

先找出左连接的结果,再找出右连接的结果,然后把这两个结果UNION即可,UNION时会自动把重复的数据过滤掉。

            var firstNames = new[]
            {
                new { ID = 1, Name = "John" },
                new { ID = 2, Name = "Sue" },
            };
            var lastNames = new[]
            {
                new { ID = 1, Name = "Doe" },
                new { ID = 3, Name = "Smith" },
            };
            var leftOuterJoin = from first in firstNames
                                join last in lastNames
                                on first.ID equals last.ID
                                into temp
                                from last in temp.DefaultIfEmpty(new { first.ID, Name = default(string) })
                                select new
                                {
                                    first.ID,
                                    FirstName = first.Name,
                                    LastName = last.Name,
                                };
            var rightOuterJoin = from last in lastNames
                                 join first in firstNames
                                 on last.ID equals first.ID
                                 into temp
                                 from first in temp.DefaultIfEmpty(new { last.ID, Name = default(string) })
                                 select new
                                 {
                                     last.ID,
                                     FirstName = first.Name,
                                     LastName = last.Name,
                                 };
            var fullOuterJoin = leftOuterJoin.Union(rightOuterJoin);

方法二:

得到左连接的数据,再从右连接的数据中把左连接的数据排除掉,两者的数据Concat一下即可

            var firstNames = new[]
            {
                new { ID = 1, Name = "John" },
                new { ID = 2, Name = "Sue" },
            };
            var lastNames = new[]
            {
                new { ID = 1, Name = "Doe" },
                new { ID = 3, Name = "Smith" },
            };
            var leftData = (from first in firstNames
                            join last in lastNames on first.ID equals last.ID into temp
                            from last in temp.DefaultIfEmpty(new { first.ID, Name = default(string) })
                            select new
                            {
                                first.ID,
                                FirstName = first.Name,
                                LastName = last.Name,
                            });

            var rightRemainingData = (from r in lastNames
                                      where !(from a in leftData select a.ID).Contains(r.ID)
                                      select new
                                      {
                                          r.ID,
                                          FirstName = default(string),
                                          LastName = r.Name
                                      });

            var fullOuterjoinData = leftData.Concat(rightRemainingData);

以上两种方法,其实是同一种方式来实现全连接的,只是第二次拿出的数据有所不同。

以上,希望对大家有所帮助。

转载于:https://www.cnblogs.com/zhaohuayang/archive/2012/11/19/2778178.html