首页 文章

获得top 3 rownum的子查询在pl / sql中不起作用

提问于
浏览
0
DECLARE
    CURSOR EMPCUR 
      SELECT EMPNO,ENAME,SAL,ROWNUM 
        FROM (SELECT * 
                FROM EMP 
               ORDER BY SAL DESC) 
       WHERE ROWNUM<=3 
       ORDER BY ROWNUM;
BEGIN
  FOR EMPREC IN EMPCUR
  LOOP
    DBMS_OUTPUT.PUT_LINE('RANK '||EMPREC.ROWNUM);
    DBMS_OUTPUT.PUT_LINE(EMPREC.EMONO||' - '||EMPREC.ENAME||' - '||EMPREC.SAL);
  END LOOP;
END;
/

此代码不起作用:

第2行的错误:ORA-06550:第2行第17列:PLS-00103:当遇到以下情况之一时遇到符号“SELECT”:(;是返回符号“is”代替“SELECT”继续 .

2 回答

  • 0

    您错过了游标声明 IS ,并且第7行 EMPREC.EMONO 中存在拼写错误 .

    试试这样,

    DECLARE
        CURSOR EMPCUR IS  SELECT EMPNO,ENAME,SAL,ROWNUM FROM (SELECT * FROM EMP ORDER BY SAL DESC) WHERE ROWNUM<=3 ORDER BY ROWNUM;
    BEGIN
        FOR EMPREC IN EMPCUR
        LOOP
            DBMS_OUTPUT.PUT_LINE('RANK '||EMPREC.ROWNUM);
            DBMS_OUTPUT.PUT_LINE(EMPREC.EMPNO||' - '||EMPREC.ENAME||' - '||EMPREC.SAL);
        END LOOP;
    END;
    /
    
  • 0

    我想建议在子查询中使用rownum伪列对事物进行排序充其量只是一种有缺陷的方法,很少实现实际目标 . 例如,您是否希望拥有前三名薪水的员工?或者你总是想要最多三条记录?这个等式如何应对薪水相同的员工?等等 .

    这是一种更好的方法来使用分析函数,在这些函数中定义您的显式排名并返回实际回答问题的结果 .

    begin
        for rec in ( select sq.*
                       from ( select e.employee_id
                                   , e.first_name ||' '|| e.last_name as full_name 
                                   , e.salary
                                   , rank() over (order by e.salary desc) as salary_rank
                                from hr.employees e ) sq
                      where sq.salary_rank <= 3
                      order by sq.salary desc )
        loop
            dbms_output.put_line('RANK ' || rec.salary_rank);
            dbms_output.put_line(rec.employee_id || ' - ' || rec.full_name || ' - ' || rec.salary);
        end loop;
    end;
    

相关问题