SQL:DISTINCT不使用游标

时间:2015-08-19 13:17:45

标签: sql oracle select cursor distinct

我遇到sql查询问题它没有返回不同的值,
具有如下所述的SQL查询

SELECT DISTINCT m.Firstname, m.Secondname, m.creation_date, 
     CURSOR (SELECT DISTINCT o.Certifications, o.Country FROM OtherTable o 
     WHERE o.OtherTable_ID = m.MainTable_ID ) details 
FROM MainTable m 
WHERE m.Manager_ID = 100

此处Maintable有20条相应管理员的记录(100),但只有一条记录可用于下面提到的列。

SELECT DISTINCT 
    m.Firstname, m.Secondname, m.creation_date 
FROM 
    MainTable m 
WHERE 
    m.Manager_ID = 100

但是当我用光标执行时它会返回所有20行,而不考虑不同的。

我尝试使用以下查询,但需要上述格式。

SELECT DISTINCT 
    m.Firstname, m.Secondname, m.creation_date, o.Certifications, o.Country 
FROM 
    MainTable m 
LEFT JOIN 
    OtherTable o  ON o.OtherTable_ID = m.MainTable_ID
WHERE 
    m.Manager_ID = 100

请您告诉我们,我们怎么能实现这一目标?

2 个答案:

答案 0 :(得分:1)

这有点难以解释,但我会尝试。

您的比较查询是

SELECT DISTINCT m.Firstname, m.Secondname, m.creation_date, 
FROM MainTable m 
WHERE m.Manager_ID = 100;

但是,您正在SELECT中使用另一个列,这也将应用于DISTINCT。因此,更好的比较是:

SELECT DISTINCT m.Firstname, m.Secondname, m.creation_date, m.MainTable_ID
FROM MainTable m 
WHERE m.Manager_ID = 100;

您可能希望DISTINCT应用于子查询返回的值。我猜 - 由于游标封装逻辑的方式 - 它被应用于相关列而不是输出列。注意:我对这种行为并不是100%肯定,并且游标表达式没有得到很好的记录。

我想不出这种行为的简单方法。

编辑:

我认为可能解决问题:

SELECT DISTINCT m.Firstname, m.Secondname, m.creation_date, 
       CURSOR (SELECT DISTINCT o.Certifications, o.Country
               FROM OtherTable o JOIN
                    MainTable m2
                    ON o.OtherTable_ID = m2.MainTable_ID
               WHERE m2.Firstname = m.Firstname and m2.Lastname = m.Lastname and
                     m2.creation_date = m.creation_date
              ) details 
FROM MainTable m 
WHERE m.Manager_ID = 100;

答案 1 :(得分:0)

看起来我们在distinct子句中放置了什么光标,结果不会崩溃(消除重复)。我已尝试使用cursor(select * from dual),当我们更改行时可能会有所不同,但似乎是。

解决方法是在选择光标之前获取不同的行:

SELECT m.Firstname, m.Secondname, m.creation_date,
       CURSOR (SELECT DISTINCT o.Certifications, o.Country 
               FROM OtherTable o 
               WHERE o.OtherTable_ID = m.MainTable_ID
               ) details 
FROM(
   SELECT m.Firstname, m.Secondname, m.creation_date, min(MainTable_ID) as MainTable_ID
   FROM MainTable m 
   WHERE m.Manager_ID = 100
   GROUP BY m.Firstname, m.Secondname, m.creation_date
) m

您还可以在内部使用选择最后一个查询形式您的问题(使用左连接)以确保您获得正确的不同行。

更新正如我在评论中所说,这只是一个如何解决的问题。应在内部选择中准备所需的行,外部选择应仅用于格式化原因(如您所指定)。