【问题标题】:Doing a Left outer join in a linq query在 linq 查询中执行左外连接
【发布时间】:2016-06-10 20:39:45
【问题描述】:

我有下面的查询,它在带有左外连接的 sqllite 中工作

        select * from customer cu
        inner join contract cnt on cu.customerId = cnt.customerid
        inner join address addy on cu.addressid = addy.addressId
        inner join csrAssoc cassc on cu.customerid = cassc.customerId
        left outer join CustomerServiceRepresentative csrr  on cassc.csrid = csrr.customerservicerepresentativeId
        inner join customerServiceManager csmm on cassc.csmid = csmm.customerservicemanagerId
        where cu.customernumber = '22222234'

我希望能够在下面的 linq 查询中在这一行上应用左外连接

        join csrr in objCsrCustServRep.AsEnumerable() on cassc.CsrId equals
                                    csrr.CustomerServiceRepresentativeId

        VisitRepData = (from cu in objCustomer.AsEnumerable()
                                join cnt in objContract.AsEnumerable() on cu.customerId equals cnt.customerId
                                join addy in objAddress.AsEnumerable() on cu.addressId equals addy.addressId
                                join cassc in objCsrAssoc.AsEnumerable() on cu.customerId equals cassc.CustomerId
                                join csrr in objCsrCustServRep.AsEnumerable() on cassc.CsrId equals
                                    csrr.CustomerServiceRepresentativeId
                                join csmm in objCustServMan on cassc.CsmId.ToString() equals csmm.customerServiceManagerId
                                where cu.CustomerNumber == (customernbr)

如何在 linq 查询中进行左外连接?

这是我调整并运行代码后的评论。还添加了其他部分。我得到的只是对象未设置为对象的实例。

         var VisitRepData = from cu in objCustomer.AsEnumerable()
                                join cnt in objContract.AsEnumerable() on cu.customerId equals cnt.customerId
                                join addy in objAddress.AsEnumerable() on cu.addressId equals addy.addressId
                                join cassc in objCsrAssoc.AsEnumerable() on cu.customerId equals cassc.CustomerId
                                join csrr in objCsrCustServRep.AsEnumerable() on cassc.CsrId equals
                                    csrr.CustomerServiceRepresentativeId into temp
                                from tempItem in temp.DefaultIfEmpty()
                                join csmm in objCustServMan on cassc.CsmId.ToString() equals csmm.customerServiceManagerId
                                where cu.CustomerNumber == (customernbr)
                                select new
                                {
                                    cu.customerId,
                                    cu.CustomerNumber,
                                    cu.customerName,
                                    cu.dateActive,
                                    cnt.contractExpirationDate,
                                    addy.street,
                                    addy.street2,
                                    addy.city,
                                    addy.state,
                                    addy.zipcode,
                                    cu.EMail,
                                    cu.phoneNo,
                                    cu.faxNumber,
                                    csmm.customerServiceManagerName,
                                    tempItem.CustomerServiceRepresentativeName,
                                };

                            foreach (var item in VisitRepData)
                            {
                                var one = item.customerId;
                                var two = item.CustomerNumber;
                            }

【问题讨论】:

  • LEFT OUTER JOIN in LINQ的可能重复
  • 您的链接中没有任何内容被标记为答案。
  • 216 票还不足以让您阅读答案吗?没有考虑到这个问题非常基础并且缺乏基础研究 - join clause (C# Reference)How to: Perform Left Outer Joins (C# Programming Guide) 等。
  • 有趣。您发送的示例的链接描述了与集合的外部连接,即两个不同的集合。我的例子对你来说看起来像一个集合吗?你的评论很粗鲁。
  • 无论 sequence 类型如何(IEnumerable<T>IQueryable<T>),查询语法模式都是相同的。与其发布 cmets,不如简单地尝试一下。我真的不明白这有什么意义。无论如何,查看更新后的帖子,您是否忘记了left outer join 包含null 右侧元素,因此必须有人检查null 以避免NRE。此外,AsEnumerable() 将导致将所有相关表加载到内存中。

标签: linq linq-to-sql


【解决方案1】:

documentation:

左外连接是返回第一个集合的每个元素的连接,无论它在第二个集合中是否有任何相关元素。 您可以使用 LINQ 通过对组连接的结果调用 DefaultIfEmpty 方法来执行左外连接

(强调我的)

根据上面的 MSDN 链接,如果我正确理解了您的要求,查询应如下所示:

    VisitRepData = from cu in objCustomer.AsEnumerable()
                            join cnt in objContract.AsEnumerable() on cu.customerId equals cnt.customerId
                            join addy in objAddress.AsEnumerable() on cu.addressId equals addy.addressId
                            join cassc in objCsrAssoc.AsEnumerable() on cu.customerId equals cassc.CustomerId
                            join csrr in objCsrCustServRep.AsEnumerable() on cassc.CsrId equals
                                csrr.CustomerServiceRepresentativeId into temp
                            from tempItem in temp.DefaultIfEmpty()
                            join csmm in objCustServMan on cassc.CsmId.ToString() equals csmm.customerServiceManagerId
                            where cu.CustomerNumber == (customernbr)

具体来说,左外连接是用这段代码执行的:

join csrr in objCsrCustServRep.AsEnumerable()
    on cassc.CsrId equals csrr.CustomerServiceRepresentativeId 
    into temp
from tempItem in temp.DefaultIfEmpty()

【讨论】:

  • 看起来不错,但需要能够拉取这个字段。 csrName = csrr.CustomerServiceRepresentativeName,这现在给我一个错误
  • @user2320476 我没有在您的原始问题中看到该字段 - 如果没有看到整个图片,很难将我的答案调整到您的特定代码;但是,左外连接应该可以工作,您应该能够根据您的情况调整我的答案。
  • 感谢 CoolBots。我添加了代码的最后一部分,得到的只是对象未设置为对象的实例。
  • 我将此行 csrr.CustomerServiceRepresentativeName 更改为 tempItem.customerServiceRepresentativeName
  • @user2320476 你解决了这个问题,还是仍然得到 NullReferenceException?如果有,哪一行代码会抛出异常?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-02-10
  • 2023-03-19
  • 1970-01-01
  • 1970-01-01
  • 2014-09-17
  • 2015-02-06
  • 1970-01-01
相关资源
最近更新 更多