Sql 为什么使用左连接时会得到不同数量的记录

Sql 为什么使用左连接时会得到不同数量的记录,sql,sql-server,tsql,join,Sql,Sql Server,Tsql,Join,我需要加入多对多关系。为了做到这一点,我正在使用 LEFT OUTER JOIN (SELECT SICCode, QuoteID FROM NetRate_Quote_Insur_Quote_Busin WHERE QuoteID IN (SELECT DISTINCT QuoteID FROM NetRate_Quote_Insur_

我需要加入多对多关系。为了做到这一点,我正在使用

LEFT OUTER JOIN  
    (SELECT 
         SICCode, QuoteID 
     FROM  
         NetRate_Quote_Insur_Quote_Busin 
     WHERE 
         QuoteID IN 
              (SELECT DISTINCT QuoteID 
               FROM NetRate_Quote_Insur_Quote_Busin)) nr  ON nr.QuoteID = tblQuotes.QuoteID
我们的目标是使专栏
SICCode
。为此,我使用
DISTINCT
语句来建立多对一的关系。但由于某种原因,我得到了不同数量的唱片

最后一个
左外连接是我一直使用的连接

完整查询如下所示:

SELECT      
    MONTH(INV.EffectiveDate) AS Effective_Month,
    tblQuotes.PolicyNumber,
    YEAR(INV.EffectiveDate) AS Effective_Year, 
    INV.EffectiveDate,
    INV.[InvoiceDate] as [Billed Date],
    tblQuotes.ExpirationDate as [Policy Expiration Date],
    INV.DueDate,
    dbo.tblFin_InvoiceDetails.AmtBilled AS Written
FROM  
    tblClientOffices
INNER JOIN 
    tblInsureds (NOLOCK) 
INNER JOIN 
    tblFin_Invoices INV
INNER JOIN 
    tblFin_InvoiceDetails ON INV.InvoiceNum = dbo.tblFin_InvoiceDetails.InvoiceNum
INNER JOIN 
    tblCompanyLines (NOLOCK) ON dbo.tblFin_InvoiceDetails.CompanyLineGuid = dbo.tblCompanyLines.CompanyLineGUID 
INNER JOIN 
    lstLines (NOLOCK) ON dbo.tblCompanyLines.LineGUID = dbo.lstLines.LineGUID 
                      AND dbo.tblCompanyLines.LineGUID = dbo.lstLines.LineGUID
INNER JOIN 
    tblProducerLocations (NOLOCK) ON INV.ProducerLocationGUID = tblProducerLocations.ProducerLocationGUID 
    ON tblInsureds.InsuredGUID = INV.InsuredGUID
INNER JOIN 
    tblQuotes (NOLOCK) ON INV.QuoteID = tblQuotes.QuoteID 
                       AND INV.QuoteControlNum = tblQuotes.ControlNo
INNER JOIN 
    lstPolicyTypes (NOLOCK) ON tblQuotes.PolicyTypeID = lstPolicyTypes.PolicyTypeID
INNER JOIN 
    tblSubmissionGroup (NOLOCK) ON tblQuotes.SubmissionGroupGuid = tblSubmissionGroup.SubmissionGroupGUID
INNER JOIN 
    tblCompanyLocations (NOLOCK) ON tblQuotes.CompanyLocationGuid = tblCompanyLocations.CompanyLocationGUID
INNER JOIN 
    tblUsers (NOLOCK) ON INV.UnderwriterUserGUID = tblUsers.UserGUID 
    ON tblClientOffices.OfficeGUID = tblQuotes.IssuingLocationGuid
LEFT OUTER JOIN 
    tblUsers tblUsers_1 (NOLOCK) ON tblSubmissionGroup.InHouseProducerUserGuid = tblUsers_1.UserGUID
LEFT OUTER JOIN  
    (SELECT SICCode, QuoteID 
     FROM NetRate_Quote_Insur_Quote_Busin 
     WHERE QuoteID IN 
           (SELECT DISTINCT QuoteID 
            FROM NetRate_Quote_Insur_Quote_Busin)) nr ON nr.QuoteID = tblQuotes.QuoteID
WHERE 
    (tblInsureds.TestInsured = 0)
    AND (INV.Failed = 0)
    AND (tblFin_InvoiceDetails.ChargeType = 'p')
ORDER BY    
    YEAR(INV.EffectiveDate), 
    MONTH(INV.EffectiveDate), 
    lstLines.LineID  
带列
SICCode
并保持相同数量的记录的诀窍是什么 我也试着这样做:

LEFT OUTER JOIN NetRate_Quote_Insur_Quote_Busin nr  ON nr.QuoteID = 
                            (
                            SELECT distinct QuoteID from NetRate_Quote_Insur_Quote_Busin
                            where QuoteID =tblQuotes.QuoteID
                            )
但它给了我更多的记录

我也试过这个:

    LEFT OUTER JOIN 
                        (   SELECT TOP 1 SICCode, QuoteID 
                            FROM NetRate_Quote_Insur_Quote_Busin 
                            WHERE QuoteID IN 
                                            (SELECT DISTINCT QuoteID 
                                                FROM NetRate_Quote_Insur_Quote_Busin)order by QuoteID desc ) nr ON nr.QuoteID = tblQuotes.QuoteID

但是不会给我带来任何SICCode

独特的
不会将多对多关系更改为多对一。看起来您的数据中有多个
SICCode
值对应一个
QuoteID
,这就是为什么您会获得更高的记录计数

您可以使用类似的窗口函数,但这是一个任意选择

您可以尝试透视/取消透视
SICCode
列,但这将为每个可能的值提供一列,如果列中有大量唯一值,则这将不起作用

最后一个选项是创建一个新表,该表有一个
QuoteID
列和一个
SICCodes
列,然后用
SICCodes
作为逗号分隔的代码列表填充它


总之,要将多对多关系更改为多对一关系并不容易,除非您愿意丢失数据或只有少数值。

DISTINCT
不会将多对多关系更改为多对一。看起来您的数据中有多个
SICCode
值对应一个
QuoteID
,这就是为什么您会获得更高的记录计数

您可以使用类似的窗口函数,但这是一个任意选择

您可以尝试透视/取消透视
SICCode
列,但这将为每个可能的值提供一列,如果列中有大量唯一值,则这将不起作用

最后一个选项是创建一个新表,该表有一个
QuoteID
列和一个
SICCodes
列,然后用
SICCodes
作为逗号分隔的代码列表填充它


总之,要将多对多关系更改为多对一关系,没有简单的方法,除非您愿意丢失数据或只有几个值。

您得到的行数不同,由于
LEFT JOIN
中的查询对于
QuoteID
的某些值,每个
QuoteID
返回多行,因此这似乎是一个金融应用程序。我强烈建议你不要再向诺洛克乱说你的问题了。当您需要准确的结果时,此查询提示将确保您在大多数情况下都拥有基本正确的信息。它可以并将返回丢失和/或重复的行。这个查询提示将执行一系列其他险恶的操作。不仅仅是肮脏的阅读。顶部(1)SICCode在这里有效吗,这意味着只返回报价的第一个SICCode?或者您需要每个代码的主记录吗?出于某种原因,TOP(1)没有为我提供任何SIC代码。All NULL'或在具有左联接的查询中的外观如何?您会得到不同的行数,因为
LEFT JOIN
中的查询对于
QuoteID
的某些值,每个
QuoteID
返回多行。这似乎是一个金融应用程序。我强烈建议你不要再向诺洛克乱说你的问题了。当您需要准确的结果时,此查询提示将确保您在大多数情况下都拥有基本正确的信息。它可以并将返回丢失和/或重复的行。这个查询提示将执行一系列其他险恶的操作。不仅仅是肮脏的阅读。顶部(1)SICCode在这里有效吗,这意味着只返回报价的第一个SICCode?或者您需要每个代码的主记录吗?出于某种原因,TOP(1)没有为我提供任何SIC代码。所有空值或它在使用左连接的查询中的外观如何?我只是查看数据,似乎相同的
SICCode
可以用于多个
QuoteID
。但是,
QuoteID
将有所不同。但是没有太多的
SICCode
值与一个
QuoteID
@Oleg听起来像逗号分隔列表选项是一个很好的选择。您将能够在不更改行数的情况下查看所有可能的选项。谢谢。你能给我举几个好例子吗?谢谢你可以试试。这可能比我想的解决方案简单。您将获得HTML编码的结果,因此您可能必须修复任何<>&字符。@Oleg其他XPATH示例:。其他选项:,我只是看看数据,似乎相同的
SICCode
可以用于多个
QuoteID
。但是,
QuoteID
将有所不同。但是没有太多的
SICCode
值与一个
QuoteID
@Oleg听起来像逗号分隔列表选项是一个很好的选择。您将能够在不更改行数的情况下查看所有可能的选项。谢谢。你能给我举几个好例子吗?谢谢你可以试试。这可能比我想的解决方案简单。您将获得HTML编码的结果,因此您可能必须修复任何<>&字符。@Oleg其他XPATH示例:。其他选择:,