PLSQL转换为CASE stmt

时间:2018-11-21 07:06:09

标签: plsql

然后将其转换为CASE stmt。请让我知道我在这里犯什么错误

DECLARE
    salary      NUMBER;
        bonus       NUMBER;
        hdate       DATE;
    empno       NUMBER;
BEGIN
    SELECT hiredate INTO hdate FROM emp where empno=7788 ;
    CASE hdate
            WHEN hdate > TO_DATE('01-JAN-82') THEN bonus := 500  DBMS_OUTPUT.PUT_LINE(bonus);
            WHEN hdate > TO_DATE('23-JAN-16') THEN bonus := 1000 DBMS_OUTPUT.PUT_LINE(bonus);
            ELSE bonus := 1500 DBMS_OUTPUT.PUT_LINE(bonus);
    END CASE;
END;
/

3 个答案:

答案 0 :(得分:3)

CASE使用以下语法:

DECLARE
    salary      NUMBER;
        bonus       NUMBER;
        hdate       DATE;
    empno       NUMBER;
BEGIN
    SELECT sysdate INTO hdate FROM dual ;
    CASE 
            WHEN hdate > TO_DATE('01-JAN-82') THEN bonus := 500;  
            WHEN hdate > TO_DATE('23-JAN-16') THEN bonus := 1000 ;
            ELSE bonus := 1500 ;
    END CASE;
    DBMS_OUTPUT.PUT_LINE(bonus);
END;
  

请注意,WHEN子句可以使用不同的条件,而不是全部测试相同的变量或使用相同的运算符。

答案 1 :(得分:2)

也许是另一个命题;而不是CASE子句中的WHERE语句,而是在SELECT列表中阻止hdate的使用,从而使用单个SQL来实现所需的输出。

DECLARE
   salary    NUMBER;
   p_bonus   NUMBER;
   hdate     DATE;
   empno     NUMBER;
BEGIN
   SELECT CASE
             WHEN hiredate > TO_DATE ('01-JAN-82') THEN 500
             WHEN hiredate > TO_DATE ('23-JAN-16') THEN 1000
             ELSE 1500
          END
     INTO p_bonus
     FROM emp
    WHERE empno = 7788;


   DBMS_OUTPUT.put_line (p_bonus);
END;
/

答案 2 :(得分:1)

除了其他答案外,您的case语句还有其他一些错误。

日期

使用to_date将字符串显式转换为日期时,还应该使用格式模型来描述字符串的格式。否则,您将依赖默认的NLS_DATE_FORMAT参数,这在不同的计算机上可能会有所不同。

此外,年份有4位数字-使用所有数字,而不是让Oracle猜测。 2位数字的年份162016还是1916

在两种情况下最好都要明确!

因此,您的日期条件实际上应该是to_date('01-JAN-1982', 'dd-MON-yyyy', 'nls_date_language=english')to_date('23-JAN-2016', 'dd-MON-yyyy')

请注意是否存在可选的第三个参数-之所以使用该参数,是因为您以字指定了月份,并且您的NLS_DATE_LANGUAGE参数在其他人的机器上可能也不相同。添加第三个参数意味着无论您的NLS设置如何,字符串都将转换为日期。

您可以避免使用to_date中的第3个参数,方法是使用日期,月份和年份的数字,例如to_date('23/01/2016', 'dd/mm/yyyy', 'nls_date_language=english')

案例和逻辑短路

CASE使用逻辑短路,这意味着当它评估条件为真时,它将不再处理任何其他条件。

您似乎打算在2017年2月23日的聘用日期中获得1000的奖金,但是由于它满足了第一个条件(比1982年1月1日晚),因此它可以获得500的奖金。

因此,您需要更改条件的顺序,以便最严格的限制在顶部。就您而言,您的过程将变为:

DECLARE
  salary NUMBER;
  bonus  NUMBER;
  hdate  DATE;
  empno  NUMBER;
BEGIN
  SELECT hiredate
  INTO   hdate
  FROM   emp
  WHERE  empno=7788;

  CASE hdate
    WHEN hdate > TO_DATE('23-JAN-16') THEN bonus := 1000;
    WHEN hdate > TO_DATE('01-JAN-82') THEN bonus := 500;
    ELSE bonus := 1500 DBMS_OUTPUT.PUT_LINE(bonus);
  END CASE;

  DBMS_OUTPUT.PUT_LINE(bonus);
END;
/