2017-07-24 285 views
0

例如,我們有僱主工資和部門基於emp表。PL/SQL定義用於求和的select語句If和循環

在SQL中,我們可以僅僅通過這樣

SELECT SUM(SAL) FROM EMP WHERE DEPTNO = 20 ; //Lets put it we finding sum for dept 20. 

但是,在其他的PL/SQL,我想我是錯的語法檢索每個部門的工資總和。我正在使用光標來存儲所有數據。在我的if語句中,在下面的循環中,我嘗試了我的邏輯

if deptno = 20 THEN 
    totalSalary = sum(salary); 
    DBMS_OUTPUT.PUT_LINE('Department : 20' || total Salary); 

這是我的實際代碼。

DECLARE 
msal emp.salary%TYPE; 
mdept emp.departmentNo%TYPE; 
new_salary number(10,2); 

CURSOR E1 IS select salary , departmentNo from emp; 


BEGIN 
OPEN E1; 
    LOOP 
    FETCH E1 into msal , mdeptno;  
     IF mdeptno = 20 THEN 
      ---- I cant seems to find the right logic here to print out the total sum for department 20--- 
     END IF; 
    EXIT WHEN E1%NOTFOUND; 
    END LOOP; 

CLOSE E1; 
END; 
/

在此先感謝

回答

0

您可以介紹的總和聚合,並在每次循環迭代增加它的另一個變量。 然後在需要時打印出來。

DECLARE 
msal emp.salary%TYPE; 
mdept emp.departmentNo%TYPE; 
sum_salary number(10,2) := 0; 

CURSOR E1 IS select salary , departmentNo from emp; 


BEGIN 
OPEN E1; 
    LOOP 
    FETCH E1 into msal , mdeptno; 
    sum_salary := sum_salary + msal; 
     IF mdeptno = 20 THEN 
      dbms_output.put_line(sum_salary); 
    EXIT WHEN E1%NOTFOUND; 
    END LOOP; 

CLOSE E1; 

PL/SQL允許您通過行可排,(由SQL做幕後爲你)

0

保持總運行與變量,totalSalary

的算法如下:從光標,e1


-fetch值,以及分配給msalmdeptno

- 適用的msal每個取值(環內),使用變量,tot_sal(或totalSalary爲您最初發布)


你的方法繼續運行總和,分配,totalSalary := sum(salary);,只會引發錯誤,因爲salary未被定義爲變量。光標取值salary(我的是sal),它被分配到msal

如果賦值爲totalSalary := sum(msal);,那麼它將寫入先前提取的值並且不記錄正在運行的總數。

標準的方式做,這是在循環之前初始化tot_sal爲零(或totalSalary),然後保持一個運行總計爲每個取記錄:

tot_sal := tot_sal + msal;

這裏是並列簡單的SQL結果匿名塊:

  [email protected]>SELECT 
     2  SUM(sal) 
     3 FROM 
     4  emp 
     5 WHERE 
     6  deptno = 20; 
    SUM(SAL) 
    10875  


    [email protected]>DECLARE 
    2  msal  emp.sal%TYPE; 
    3  mdeptno emp.deptno%TYPE; 
    4  tot_sal emp.sal%TYPE; 
    5  CURSOR e1 IS 
    6   SELECT 
    7    sal, 
    8    deptno 
    9   FROM 
10    emp; 
11 
12 BEGIN 
13  tot_sal := 0; 
14  OPEN e1; 
15  LOOP 
16   FETCH e1 INTO msal,mdeptno; 
17   IF 
18    mdeptno = 20 
19   THEN 
20    tot_sal := tot_sal + msal; 
21   END IF; 
22 
23   EXIT WHEN e1%notfound; 
24  END LOOP; 
25 
26  CLOSE e1; 
27  dbms_output.put_line(tot_sal); 
28 END; 
29/
10875 


PL/SQL procedure successfully completed. 
0

有沒有必要使用PL/SQL的東西,你可以用SQL做。但是,如果你真的需要它,使用下列內容:

DECLARE 
    msal emp.salary%TYPE; 
    mdept emp.departmentNo%TYPE; 
    new_salary number(10,2); 

    CURSOR E1 (p_dept number) IS 
    select sum(salary) from emp where departmentNo = p_dept; 


BEGIN 
    OPEN E1(20); 
    FETCH E1 into msal;  
    dbms_output.put_line(msal); 
    CLOSE E1; 
END; 
/
0

感謝您對您的所有響應, 我分配到這樣做在PL/SQL,

我明白從你們那裏所有的響應。
我已經拿出最簡單的技術來得到sum,min,max和avg的結果。

我基本上做的是使用已經在sql中的inbuild函數,並在我的select語句中實現它。所以,我有

DECLARE 
totalSal emp.salary%TYPE; 
maxSal emp.salary%TYPE; 
minSal emp.salary%TYPE; 
mdept emp.departmentNo%TYPE := 20; /* for an example getting all values for dept 20 */ 

CURSOR E1 IS select sum(salary) , max(salary) , min(sal) from emp where 
departmentNo = mdept group by departmentNo; 


BEGIN 

    OPEN E1; 
     LOOP 
     FETCH E1 into totalSal , maxSal , minSal; 
     EXIT WHEN E1%NOTFOUND; 

     DBMS_OUTPUT.PUT_LINE('...' || maxsal); /*...so on for display*/ 
     END LOOP; 

    CLOSE E1; 

    END;/
+0

解決這個問題,您可以使用[遊標FOR循環(http://docs.oracle.com/database/121/LNPLS/cursor_for_loop_statement.htm)建設簡化循環,節省了一堆的代碼。但對於單行查詢,無論如何都不需要循環。 –