PL / SQL匿名块'精确提取返回超过请求的行数'

时间:2013-02-12 09:36:51

标签: sql oracle plsql

我一直在研究PL / SQL脚本,它计算两个食谱之间的相似性。 Recipe 是包含所有标题,准备等的表格。 Ingredient 是存储所有独特成分的地方,配方是许多很多问题都解决了,两者有联系。

CREATE OR REPLACE FUNCTION func_similarity
  (idS1 IN recipes.recipe.recipeID%type , idS2 IN recipes.recipe.recipeID%type ) 
  RETURN NUMBER 
AS 
sim_value NUMBER := 0;
BEGIN
SELECT  2* 
    (select count(*) from recipes.ingredient i where i.ingredientID in (
      Select distinct ingredientID from recipes.recipeing where recipeID = s1.recipeID
      intersect
      select distinct ingredientID from recipes.recipeing  where recipeID = s2.recipeID))  
     /      ((select distinct count(ingredientID) from RECIPES.recipeing where recipeID = s1.recipeID) +
         (select distinct count(ingredientID) from recipes.recipeing where recipeID = s2.recipeID) )   INTO sim_value
from recipes.recipe s1, recipes.recipe s2
where s1.recipeID = idS1
and s2.recipeID = idS2;

RETURN (sim_value);
END func_similarity;
/

然而,当我使用匿名块测试它时,我收到错误: “确切提取的次数超过了请求的行数”

declare
v_sim number;
begin
v_sim:=func_similarity(1,4);
dbms_output.put_line(v_sim);
end;
/

现在,我非常确定这个功能有意义且应该工作(整个周末都带我去)。有没有人知道为什么这可能不起作用?

提前致谢。

2 个答案:

答案 0 :(得分:1)

两个表之间没有链接:

from recipes.recipe s1, recipes.recipe s2
where s1.recipeID = idS1
and s2.recipeID = idS2;

因此,查询是交叉连接。如果recipeID是主键,则无关紧要。但是,如果该列中有重复的数字,则查询将返回多行。如果你的查询返回多行,你的函数将抛出一个TOO_MANY_ROWS异常,因为我们只能选择一行INTO变量(除非我们使用BULK COLLECT INTO一个集合变量 。

答案 1 :(得分:0)

只应将1行返回到sim_value。要查看发生了什么,请运行不带INTO的SQL并使用IDS1和IDS2的值。