2013-07-12 210 views
0

存储过程存在问题。 它失败在以下情况下Oracle存储过程失败

cntmismatch NUMBER; 

SELECT COUNT(keyvalue) INTO cntmismatch 
FROM tbl_temp GROUP BY keyvalue HAVING count(keyvalue) > 1 

当存在上述标准没有数据,它失败

我甚至使用

SELECT NVL(COUNT(keyvalue),0) INTO cntmismatch 
FROM tbl_temp GROUP BY keyvalue HAVING count(keyvalue) > 1 

尝试,但它仍然retuns我这里空和PROC失败

+0

请解释一下你正在试图解决什么问题。正如你从答案中看到的那样,有许多可能的解决方案,但它们解决了不同的问题。作为一项规则,通常最好告诉我们您要实施的业务规则,而不是期望我们从一些失败的代码中猜测它们。 – APC

回答

1

如果要计算keyvalue出现的次数不止一次,则需要使用子选择:

SELECT COUNT(*) INTO cntmismatch 
FROM 
(SELECT keyvalue, count(*) FROM tbl_temp GROUP BY keyvalue HAVING count(*) > 1) 
3

查询:

SELECT COUNT(keyvalue) INTO cntmismatch FROM tbl_temp GROUP BY keyvalue 

...将尝试返回一行到cntmismatch为每keyvalue,如果有不止这将失败,并no_data_found如果表是空的,并与too_many_rows一个keyvalue

添加:

HAVING count(keyvalue) > 1 

...意味着它只能与多个条目,明确返回任何keyvalue的值,所以现在你会得到no_data_found如果表是空的,或者没有keyvalue出现两次;和too_many_rows如果多个keyvalue有重复。它只会在您有一个keyvalue重复的情况下才有效。

您还没有表现出你的逻辑的休息,但想必你正在做基于一个返回值的东西,在这种情况下 - 如果只有一个keyvalue,这是不可能的 - 你可以离开了HAVING条款而只是测试值:

SELECT COUNT(keyvalue) INTO cntmismatch FROM tbl_temp GROUP BY keyvalue; 
IF cntmismatch > 1 THEN 
    ... -- some processing 
END IF: 

但充其量,所有它告诉你的是是否存在多次出现任何keyvalue;它不会告诉你它们是什么keyvalue,并且仍然不能应付多于一个。

如果你想检索所有具有超过一个匹配行,做一些与他们那么你可以使用游标值:

FOR dup_keyvalues IN (SELECT keyvalue, COUNT(*) AS cnt 
    FROM tbl_temp GROUP BY keyvalue HAVING COUNT(*) > 1) LOOP 
    ... - some processing, e.g. 
    DBMS_OUTPUT.PUT_LINE('keyvalue ' || dup_keyvalues.keyvalue 
     || ' has ' || dup_keyvalues.cnt || ' matches'); 
    ... 
END LOOP; 
0

您应该简单地捕获并处理在代码中的异常。 在你的情况下,你会得到一个NO_DATA_FOUND异常。

下面你会找到一个例子。

PROCEDURE count_mismatch AS 
    cntmismatch NUMBER; 
BEGIN 
    BEGIN 
    SELECT COUNT(keyvalue) INTO cntmismatch FROM tbl_temp GROUP BY keyvalue; 
    EXCEPTION 
    WHEN no_data_found THEN 
    cntmismatch := -1; 
    END; 
END 

我认为,您不再需要HAVING子句。因此我已将其删除。 如果您的语句将返回超过预期的1行,那么您还必须处理TOO_MANY_ROWS异常!

0

试试这个

BEGIN 
    SELECT COUNT(keyvalue) INTO cntmismatch 
    FROM tbl_temp GROUP BY keyvalue HAVING count(keyvalue) > 1 
EXCEPTION 
    WHEN no_data_found THEN cntmismatch := 0; 
END;