如何选择内部连接没有重复的行?

时间:2009-11-30 20:20:12

标签: sql sql-server

我的MS SQL Server stored procedure是:

set ANSI_NULLS ON
set QUOTED_IDENTIFIER ON
GO
ALTER PROCEDURE [dbo].[sp_close]
@DATE NVARCHAR(8)
AS
BEGIN
SELECT appointment_datas.appointment_date
        ,appointment_datas.appointment_no
        ,costumer_datas.costumer_name
        ,appointment_datas.appointment_type
        ,personel_datas.personel_ADI
FROM [LONI].[dbo].appointment_datas
        INNER JOIN [LONI].[dbo].costumer_datas ON appointment_datas.appointment_costumer = costumer_datas.costumer_id
        INNER JOIN [LONI].[dbo].personel_datas ON appointment_datas.appointment_personel = personel_datas.personel_id
        INNER JOIN [GUONU].[dbo].dayend ON appointment_datas.appointment_no <> dayend.appointment_no COLLATE Turkish_CI_AS
WHERE CONVERT(nvarchar(8),appointment_datas.appointment_date,112) = @DATE
END

使用此代码,我从相同的记录中选择重复的行。其实我想从[LONI]。[dbo] .appointment_datas中选择字段但是如果在约会_no 不在[GUONU]。[dbo] .dayend

4 个答案:

答案 0 :(得分:4)

SELECT DISTINCT删除输出中的重复项。

但你的SQL看起来错了。你确定要写:

TABLE1.FIELD1 <> TABLE1.FIELD1

这始终是假的。我认为您的SQL可能有错误,这可能就是您获得重复值的原因。您应该很少在join子句中使用<>,并且双方不应该使用相同的字段。

也许你打算:

ON [DB1].[dbo].TABLE1.FIELD1 <> [DB2].[dbo].TABLE1.FIELD1

但这将生成所有不匹配行的笛卡尔积。我怀疑这是你的意思。也许你想要这个:

ON [DB1].[dbo].TABLE1.ID = [DB2].[dbo].TABLE1.ID
WHERE[DB1].[dbo].TABLE1.FIELD1 <> [DB2].[dbo].TABLE1.FIELD1

这匹配每个数据库中具有相同ID但在某列中不同的行。请注意<>不在JOIN子句中。

---更新---

也许您的意思是从两个不同的数据库中选择结果,然后将它们联合起来?

SELECT appointment_datas.appointment_date 
        ,appointment_datas.appointment_no
        ,costumer_datas.costumer_name
        ,appointment_datas.appointment_type
        ,personel_datas.personel_ADI
FROM [LONI].[dbo].appointment_datas  
        INNER JOIN [LONI].[dbo].costumer_datas ON appointment_datas.appointment_costumer = costumer_datas.costumer_id
        INNER JOIN [LONI].[dbo].personel_datas ON appointment_datas.appointment_personel = personel_datas.personel_id
WHERE CONVERT(nvarchar(8),appointment_datas.appointment_date,112)

UNION

SELECT appointment_datas.appointment_date 
        ,appointment_datas.appointment_no
        ,costumer_datas.costumer_name
        ,appointment_datas.appointment_type
        ,personel_datas.personel_ADI
FROM [GUONU].[dbo].appointment_datas  
        INNER JOIN [GUONU].[dbo].costumer_datas ON appointment_datas.appointment_costumer = costumer_datas.costumer_id
        INNER JOIN [GUONU].[dbo].personel_datas ON appointment_datas.appointment_personel = personel_datas.personel_id
WHERE CONVERT(nvarchar(8),appointment_datas.appointment_date,112)

---解决方案---

在WHERE子句中使用NOT EXISTS。阅读评论以了解原因。

答案 1 :(得分:2)

该行

INNER JOIN [DB2].[dbo].TABLE1 ON TABLE1.FIELD1 <> TABLE1.FIELD1 

毫无意义,你想改写一下......

答案 2 :(得分:1)

如果我理解你的问题(在你编辑之后)

  

但如果不在约会_no   [GUONU] [DBO] .dayend

,你实际上想要一个NOT EXISTS子查询:

set ANSI_NULLS ON 
set QUOTED_IDENTIFIER ON
GO
ALTER PROCEDURE [dbo].[sp_close]
@DATE NVARCHAR(8)
AS
BEGIN
SELECT appointment_datas.appointment_date 
        ,appointment_datas.appointment_no
        ,costumer_datas.costumer_name
        ,appointment_datas.appointment_type
        ,personel_datas.personel_ADI
FROM [LONI].[dbo].appointment_datas  
        INNER JOIN [LONI].[dbo].costumer_datas ON appointment_datas.appointment_costumer = costumer_datas.costumer_id
        INNER JOIN [LONI].[dbo].personel_datas ON appointment_datas.appointment_personel = personel_datas.personel_id
WHERE CONVERT(nvarchar(8),appointment_datas.appointment_date,112) = @DATE 
  AND NOT EXISTS (SELECT 'X' FROM [GUONU].[dbo].dayend WHERE dayend.appointment_no = appointment_datas.appointment_no)     
END

答案 3 :(得分:0)

SELECT DISTINCT TABLE1.FIELD1 ,TABLE2.FIELD1 ,TABLE1.FIELD3 ,TABLE3.FIELD1 来自......

在某些变体中,您必须将字段列表括起来,即 SELECT DISTINCT(TABLE1.FIELD1 ,TABLE2.FIELD1 ,TABLE1.FIELD3 ,TABLE3.FIELD1)FROM ...