2011-08-26 140 views
3

我有一个查询,我目前正在获取ORA-01427:单行子查询返回多个行错误。我明白这个错误,是什么造成的,但无法找出解决的办法。我也想在一个查询中做到这一点。以下是我目前有:需要困难的SQL查询帮助

SELECT v1.internal_code, 
     (SELECT terms_id 
      FROM terms 
     WHERE term_start_date = 
        (SELECT MIN (term_start_date) 
         FROM terms 
         WHERE terms_id LIKE '%SU' 
           AND term_start_date > 
            (SELECT term_start_date 
             FROM  terms 
               JOIN 
               vals 
               ON terms_id = 
                internal_code 
             WHERE internal_code = 
               v1.internal_code 
               AND valcode_id = 
                'TERMS'))) 
      AS mmTerm 
FROM  terms 
     JOIN 
      vals v1 
     ON terms_id = internal_code 
    WHERE internal_code LIKE '%SP' AND valcode_id = 'WEB.SEARCH.TERMS' 
ORDER BY mmTerm ASC 

而且丘壑表的相关部分将是这样的:

internal_code  valcode_id 
-------------  ---------- 
    2003SP   TERMS 
    2004SP   TERMS 
    2005SP   TERMS 

好了,大子查询试图获取与“SU结束的任何条款'term_start_date大于vals表中术语的term_start_date。所以期望的结果是:

v1.internal_code  mmTerm 
----------------  ------ 
    2003SP   2003SU 
    2004SP   2004SU 
    2005SP   2005SU 

我知道这很难理解,所以请问如果有任何问题。此外,任何建议都很乐意接受。谢谢!

编辑:我想通了。只需做一些修改,谢谢你的建议。我会发布它,如果任何人有兴趣看到最后的查询

+0

它是mysql还是microsoft sql server? – reggie

+0

这我不确定,我使用Oracle 10g的Toad。这听起来是对的吗? – Dan

+0

这似乎意味着'terms'中有多行具有'term_start_date'的相同值。是这种情况,如果是这样,为什么?似乎多个词语应该没有相同的开始日期。 –

回答

0

这很难读 - 你需要添加别名到所有的表引用。如果您不关心子查询返回哪一行,则可以得到错误 - 只需返回MIN(terms_id)或MAX(terms_id)或其他任何仅返回1行的内容。但是,您可能需要更深入地考虑数据 - 子查询所返回的术语真的很重要吗?

SELECT v1.internal_code, 
     (SELECT MIN(terms_id) 
      FROM terms 
     WHERE term_start_date = 
        (SELECT MIN (term_start_date) 
         FROM terms 
         WHERE terms_id LIKE '%SU' 
           AND term_start_date > 
            (SELECT term_start_date 
             FROM  terms 
               JOIN 
               vals 
               ON terms_id = 
                internal_code 
             WHERE internal_code = 
               v1.internal_code 
               AND valcode_id = 
                'TERMS'))) 
      AS mmTerm 
FROM  terms 
     JOIN 
      vals v1 
     ON terms_id = internal_code 
    WHERE internal_code LIKE '%SP' AND valcode_id = 'WEB.SEARCH.TERMS' 
ORDER BY mmTerm ASC 
+0

我知道min/max只返回一行,但这不是问题。每个春季我都需要相应的夏季学期。 – Dan

+0

您是否运行我的查询? – TrojanName

+0

最接近正确,所以我会标记为已接受。 – Dan

0

您是否期待只有一条记录匹配子查询条件? 应该比你一个TOP 1添加到您的子查询:

... 
(SELECT TOP 1 terms_id ... 
+0

这不是获取错误的子查询的一部分。最内层的子查询是发生错误的地方(SELECT term_start_date .....)。所以它几乎看起来像整个查询需要被另一个子查询包装,但我还没有完全想到它 – Dan

+0

好吧,还有一个,正确的。看到@Bohemian的答案。但是外层子查询有相同的问题:它会返回多行。 – Jan

1

的问题是在子查询用在这里:AND term_start_date > ...

它必须返回一个值。最好的解决办法,我认为是使用MAX()

AND term_start_date > 
    (SELECT MAX(term_start_date) -- USE MAX HERE 
    FROM terms 
    JOIN vals 
    ON terms_id = internal_code 
    WHERE internal_code = v1.internal_code 
    AND valcode_id = 'TERMS') 

使用MAX()意味着term_start_date必须大于所有term_start_date子查询中找到)。

如果您需要它大于任何,请改为使用MIN()

EDITED我发誓你编辑了你原来的查询!无论如何,尝试使用外部选择的集合,像这样:

SELECT v1.internal_code, 
    (SELECT MAX(terms_id) 
     FROM terms 
     ... 
+0

是的,我知道这一点,不幸的是,如果你使用MAX(term_start_date),你会得到相同的错误,但是在整个子查询中。 – Dan

+0

你真的尝试过吗?因为我认为你错了:没有其他地方可以得到这个错误,并且使用MAX修复了这个问题 – Bohemian

+0

@Bohemian:最外面的子查询可能会产生相同的错误 - 请参阅我的回答 – Jan