FOR循环中的SELECT语句出错

时间:2016-03-18 12:52:20

标签: sql oracle plsql

当我尝试执行下面的代码时,我在此处收到此错误:

  

错误(9,4):PLS-00103:期待时遇到符号“SELECT”   以下之一:() - + case mod new not null table continue avg count current current max min before sql   stddev sum variance执行multiset两个前导尾随   forall合并年月日小时分秒timezone_hour   timezone_minute timezone_region timezone_abbr时间戳   间隔日期

CREATE OR REPLACE PROCEDURE PROC_LIST_SIMILAR_TVSERIES
(seriesName IN SERIES.NAME%TYPE)
AS
  CURSOR series IS (SELECT IDS FROM SERIES WHERE NAME = seriesName);
  allSeries SERIES%ROWTYPE;
BEGIN
FOR series IN allSeries
  (SELECT 2* ( SELECT COUNT(*)
               FROM   DICT d
               WHERE  d.idt IN ( SELECT DISTINCT IDT
                                 FROM   POSTING
                                 WHERE  IDS = series
                               INTERSECT
                                 SELECT DISTINCT IDT
                                 FROM   POSTING
                                 WHERE IDS = allSeries.IDS
                               )
             )
         / ( ( SELECT DISTINCT COUNT(IDT)
               FROM   POSTING
               WHERE  IDS = series
             ) +
             ( SELECT DISTINCT COUNT(IDT)
               FROM   POSTING
               WHERE  IDS = allSeries.IDS )
           )
  INTO   similarity
  FROM   SERIES s1
         SERIES s2
  WHERE  s1.IDS = series
  AND    s2.IDS != series
  );

  IF similarity > 0.7 THEN 
    DBMS_OUTPUT.PUT_LINE('ok');
  END LOOP;
END;
/

代码所做的是获取名称,找到它的ID,并将其与其他ID进行比较(并避免将其与同一ID进行比较)。当相似度计算超过0.7时,我试图打印出“ok”。不知道为什么这不起作用。

2 个答案:

答案 0 :(得分:0)

  

我仍在尝试理解SQL语句中的逻辑。但是我   有希望尝试删除语法错误。希望它有所帮助。

CREATE OR REPLACE PROCEDURE PROC_LIST_SIMILAR_TVSERIES(
    seriesName IN SERIES.NAME%TYPE)
AS
similarity PLS_INTEGER;
BEGIN
  FOR i IN
  (SELECT IDS FROM SERIES WHERE NAME = seriesName
  )
  LOOP
    --The logic i am still not able to understand
    SELECT          *,
      (SELECT COUNT(*)
      FROM DICT d
      WHERE d.idt IN
        ( SELECT DISTINCT IDT FROM POSTING WHERE IDS = I.IDS
        INTERSECT
        SELECT DISTINCT IDT
        FROM POSTING
        WHERE IDS = allSeries.IDS
        ) / (
        (SELECT DISTINCT COUNT(IDT) FROM POSTING WHERE IDS = i.IDS
        ) +
        (SELECT DISTINCT COUNT(IDT) FROM POSTING WHERE IDS = I.IDS
        ) )
      )
    INTO similarity
    FROM SERIES s1,
      SERIES s2
    WHERE s1.IDS  = s2.IDS
    AND s2.IDS   != I.IDS;
    IF similarity > 0.7 THEN
      DBMS_OUTPUT.PUT_LINE('ok');
    END IF;
  END LOOP;
END;
/

答案 1 :(得分:0)

首先,如果你有一个与表名相同的游标,那么系列%rowtype会是什么样子?光标还是表?不好的主意。

其次,你永远不会执行游标来获取ID,因此你的后续游标循环正在查找与allSeries.IDS匹配的记录,因为你还没有填充它。

尝试将此作为起点,尽管我猜测您仍然需要对光标查询进行操作。不过,至少它指出了正确的代码结构......

CREATE OR REPLACE PROCEDURE PROC_LIST_SIMILAR_TVSERIES
   (seriesName IN SERIES.NAME%TYPE)
AS 
   CURSOR seriesCur IS (SELECT IDS FROM SERIES WHERE NAME = seriesName);

   allSeries seriesCur%ROWTYPE;

BEGIN
  OPEN seriesCur;
  FETCH seriesCur INTO allSeries;
  IF seriesCur%NOTFOUND
  THEN
    CLOSE seriesCur;
    raise_application_error(-20001,'Your SeriesName does not exist');
  END IF;
  CLOSE seriesCur;

 FOR seriesRec IN 
   -- this query is a mess! Tried to fix up some aspects of it according to what I THINK you're trying to do. 
  (SELECT 2*
  (SELECT COUNT(*) FROM DICT d WHERE d.idt IN (
  SELECT DISTINCT IDT FROM POSTING WHERE IDS = allSeries.IDS
  INTERSECT
  SELECT DISTINCT IDT FROM POSTING WHERE IDS = allSeries.IDS))
  / ((SELECT DISTINCT COUNT(IDT) FROM POSTING WHERE IDS = allSeries.IDS) +
  (SELECT DISTINCT COUNT(IDT) FROM POSTING WHERE IDS = allSeries.IDS) ) similarity
  FROM SERIES s1, SERIES s2
  WHERE s1.IDS = allSeries.IDS
  AND s2.IDS != allSeries.IDS)
LOOP

    IF seriesRec.similarity > 0.7 THEN 
      DBMS_OUTPUT.PUT_LINE('ok'); 
    END IF;
END LOOP;
END;
/