0

我是 PL/SQL 的新手,我被困在无法按部门名称对数据进行分组的这一点上。我的查询如下

DECLARE
      CURSOR dept_cur IS

      select department_name ,  NVL(employee_name , 'N/A') , NVL(employee.JOB , 'N/A') ,                    NVL(to_char(hire_date, 'DD-MON-YYYY') , 'N/A')
      FROM department FULL OUTER JOIN employee ON department.department_id = employee.department_id 
      order by department_name , employee_name;

      v_department_name department.department_name%TYPE;
      v_employee_name  employee.employee_name%type;
      v_employee_job  employee.job%type;
      v_hire_date  VARCHAR(20);

BEGIN
        OPEN dept_cur;
        fetch dept_cur into v_department_name , v_employee_name , v_employee_job , v_hire_date ;

        IF dept_cur%FOUND THEN
        DBMS_OUTPUT.PUT_LINE('DEPARTMENT_NAME     EMPLOYEE NAME , EMPLOYEE JOB , HIRE DATE');
        DBMS_OUTPUT.PUT_LINE('-----------------------------------------------------');

         WHILE dept_cur%FOUND LOOP
                DBMS_OUTPUT.PUT_LINE(lpad(v_department_name, 11) || lpad(v_employee_name, 16) || lpad(v_employee_job, 22)|| lpad(v_hire_date,15));
                fetch dept_cur into v_department_name , v_employee_name , v_employee_job , v_hire_date ;
      END LOOP;

      ELSE
          DBMS_OUTPUT.PUT_LINE('No output.');
      END IF;



      CLOSE dept_cur;

END;

我希望输出是这样的,但我的查询返回整个列表。

ACCOUNTING 的员工人数为 2

EMPLOYEE_NAME           JOB                          HIRE DATE
--------------------------------------------------------------
JONES                   PUBLIC ACCOUNTANT            02-APR-81
STEEL                   PUBLIC ACCOUNTANT            02-MAR-83

其他部门也一样。我了解它在 PL SQL 块逻辑中的微小变化,但我无法弄清楚。

4

1 回答 1

0
DECLARE
    CURSOR dept_cur IS
        SELECT department_name,
            COUNT(employee.employee_id) OVER (PARTITION BY department_name),
            NVL(employee_name, 'N/A'),
            NVL(employee.JOB, 'N/A'),
            NVL(to_char(hire_date, 'DD-MON-YYYY'), 'N/A')
        FROM department
        FULL OUTER JOIN employee ON department.department_id = employee.department_id 
        ORDER BY department_name, employee_name;

    v_department_name    department.department_name%TYPE;
    last_department_name department.department_name%TYPE;
    v_department_count   NUMBER;
    v_employee_name      employee.employee_name%TYPE;
    v_employee_job       employee.job%TYPE;
    v_hire_date          VARCHAR(20);

BEGIN
    OPEN dept_cur;
    FETCH dept_cur INTO v_department_name, v_department_count, v_employee_name, v_employee_job, v_hire_date;
    last_department_name := NULL;

    IF dept_cur%FOUND THEN
        WHILE dept_cur%FOUND LOOP
            IF last_department_name IS NULL OR last_department_name <> v_department_name THEN
                DBMS_OUTPUT.PUT_LINE('The number of employees in ' || v_department_name || ' is ' || to_char(v_department_count));
                DBMS_OUTPUT.PUT_LINE('EMPLOYEE NAME           EMPLOYEE JOB                 HIRE DATE');
                DBMS_OUTPUT.PUT_LINE('--------------------------------------------------------------');
                last_department_name := v_department_name;
            END IF;

            DBMS_OUTPUT.PUT_LINE(rpad(v_employee_name, 24) || rpad(v_employee_job, 24)|| lpad(v_hire_date,14));

            FETCH dept_cur INTO v_department_name, v_department_count, v_employee_name, v_employee_job, v_hire_date;
        END LOOP;
    ELSE
        DBMS_OUTPUT.PUT_LINE('No output.');
    END IF;

    CLOSE dept_cur;
END;

它使用分析函数 COUNT() OVER ()计算每个部门结果中的员工人数,并将其插入该部门的每一行。

由于查询已经按部门排序,它只检查何时更改为另一个值,然后打印标题。

于 2012-07-31T02:44:01.927 回答