ORACLE PL/SQL函数已成功创建,但执行体不工作

ORACLE PL/SQL函数已成功创建,但执行体不工作,sql,oracle,plsql,Sql,Oracle,Plsql,以下是我创建的表列表,并为创建的表插入了值: CREATE TABLE DEPARTMENT (DEPARTMENT_ID NUMBER PRIMARY KEY, DEPARTMENT_NAME VARCHAR(30) NOT NULL ); CREATE TABLE JOBS (JOB_ID NUMBER PRIMARY KEY, JOB_TITLE VARCHAR(35) NOT NULL, MIN_SALARY DECIMAL NOT NULL, MAX_SALARY

以下是我创建的表列表,并为创建的表插入了值:

CREATE TABLE DEPARTMENT
(DEPARTMENT_ID NUMBER PRIMARY KEY,
 DEPARTMENT_NAME VARCHAR(30) NOT NULL
 );

 CREATE TABLE JOBS
 (JOB_ID NUMBER PRIMARY KEY,
  JOB_TITLE VARCHAR(35) NOT NULL,
  MIN_SALARY DECIMAL NOT NULL,
  MAX_SALARY DECIMAL NOT NULL
  );

 CREATE TABLE EMPLOYEES
(EMPLOYEE_ID NUMBER PRIMARY KEY,
 FIRST_NAME VARCHAR(20) NOT NULL,
 LAST_NAME VARCHAR(25) NOT NULL,
 EMAIL VARCHAR(25) NOT NULL,
 PHONE_NUMBER VARCHAR(20) NOT NULL,
 HIRE_DATE DATE NOT NULL,
 JOB_ID NUMBER NOT NULL,
 SALARY DECIMAL NOT NULL,
 DEPARTMENT_ID NUMBER NOT NULL,
 CONSTRAINT emp_job_fk FOREIGN KEY(JOB_ID) REFERENCES JOBS(JOB_ID),
 CONSTRAINT emp_department_fk FOREIGN KEY(DEPARTMENT_ID) REFERENCES DEPARTMENT(DEPARTMENT_ID)
 );

INSERT INTO DEPARTMENT (DEPARTMENT_ID,DEPARTMENT_NAME)
VALUES(1,'IT');
INSERT INTO DEPARTMENT (DEPARTMENT_ID,DEPARTMENT_NAME)
VALUES(2,'Sales');

INSERT INTO JOBS (JOB_ID,JOB_TITLE,MIN_SALARY,MAX_SALARY)
VALUES (1,'IT Administrator',250000.00,50000.00);
INSERT INTO JOBS (JOB_ID,JOB_TITLE,MIN_SALARY,MAX_SALARY)
VALUES (2,'Salesman',200000.00,40000.00);

INSERT INTO EMPLOYEES (EMPLOYEE_ID,FIRST_NAME,LAST_NAME,EMAIL,PHONE_NUMBER,HIRE_DATE,JOB_ID,SALARY,DEPARTMENT_ID)
VALUES (1,'Tony','Starc','starc@gmail.com','0123456789',TO_DATE('15/1/2008','DD/MM/YYYY'),1,45000.00,1);
INSERT INTO EMPLOYEES (EMPLOYEE_ID,FIRST_NAME,LAST_NAME,EMAIL,PHONE_NUMBER,HIRE_DATE,JOB_ID,SALARY,DEPARTMENT_ID)
VALUES (2,'Bruce','Wayne','bruce@gmail.com','0123456788',TO_DATE('15/1/2009','DD/MM/YYYY'),1,40000.00,1);
INSERT INTO EMPLOYEES (EMPLOYEE_ID,FIRST_NAME,LAST_NAME,EMAIL,PHONE_NUMBER,HIRE_DATE,JOB_ID,SALARY,DEPARTMENT_ID)
VALUES (3,'Larry','Ellison','larry@gmail.com','0123456787',TO_DATE('15/1/2010','DD/MM/YYYY'),1,30000.00,1);
INSERT INTO EMPLOYEES (EMPLOYEE_ID,FIRST_NAME,LAST_NAME,EMAIL,PHONE_NUMBER,HIRE_DATE,JOB_ID,SALARY,DEPARTMENT_ID)
VALUES (4,'Steve','Jobs','steve@gmail.com','0123456786',TO_DATE('15/1/2011','DD/MM/YYYY'),2,35000.00,2);
INSERT INTO EMPLOYEES (EMPLOYEE_ID,FIRST_NAME,LAST_NAME,EMAIL,PHONE_NUMBER,HIRE_DATE,JOB_ID,SALARY,DEPARTMENT_ID)
VALUES (5,'Remy','Lebeau','remy@gmail.com','0123456785',TO_DATE('15/1/2012','DD/MM/YYYY'),2,30000.00,2);
INSERT INTO EMPLOYEES (EMPLOYEE_ID,FIRST_NAME,LAST_NAME,EMAIL,PHONE_NUMBER,HIRE_DATE,JOB_ID,SALARY,DEPARTMENT_ID)
VALUES (6,'Clark','Kent','clark@gmail.com','0123456784',TO_DATE('15/1/2013','DD/MM/YYYY'),2,35000.00,2);
现在在我的作业问题中,我被要求解决以下问题: 编写一个名为fn_emps_per_dept_jc450912的函数,以检索具有给定部门ID的员工ID、姓氏、姓氏和职务。此函数应将部门ID作为输入参数,并将员工ID、姓氏、姓氏和职务标题作为输出参数。如果发现,则返回TRUE,如果未找到则返回FALSE。

为了显示特定部门员工的信息,我编写了以下函数:

CREATE OR REPLACE FUNCTION fn_emps_per_dept_jc450912 (f_dept_id IN NUMBER,f_emp_id OUT NUMBER,f_first_name OUT VARCHAR,f_last_name OUT VARCHAR,f_job_title OUT VARCHAR)
RETURN BOOLEAN
AS
BEGIN
SELECT EMPLOYEE_ID,FIRST_NAME,LAST_NAME,JOB_TITLE
INTO f_emp_id,f_first_name,f_last_name,f_job_title
FROM EMPLOYEES,JOBS,DEPARTMENT
WHERE DEPARTMENT.DEPARTMENT_ID = EMPLOYEES.DEPARTMENT_ID
AND JOBS.JOB_ID = EMPLOYEES.JOB_ID
AND EMPLOYEES.DEPARTMENT_ID = f_dept_id;
RETURN TRUE;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
DBMS_OUTPUT.PUT_LINE('Employee not found');
RETURN FALSE;
END fn_emps_per_dept_jc450912;

Function FN_EMPS_PER_DEPT_JC450912 compiled
DECLARE
f_dept_id NUMBER;
f_emp_id NUMBER;
f_first_name VARCHAR(30) ;
f_last_name VARCHAR(30) ;
f_job_title VARCHAR(30);
f_return BOOLEAN;
BEGIN
f_dept_id := 1;
f_return := fn_emps_per_dept_jc450912(f_dept_id,f_emp_id,f_first_name,f_last_name,f_job_title);
DBMS_OUTPUT.PUT_LINE('Employee_ID: ' || f_emp_id);
DBMS_OUTPUT.PUT_LINE('First Name: ' || f_first_name);
DBMS_OUTPUT.PUT_LINE('Last Name: ' || f_last_name);
DBMS_OUTPUT.PUT_LINE('Job: ' || f_job_title);
END;
从上面可以看出,该函数已成功编译

然后我尝试执行该函数:

CREATE OR REPLACE FUNCTION fn_emps_per_dept_jc450912 (f_dept_id IN NUMBER,f_emp_id OUT NUMBER,f_first_name OUT VARCHAR,f_last_name OUT VARCHAR,f_job_title OUT VARCHAR)
RETURN BOOLEAN
AS
BEGIN
SELECT EMPLOYEE_ID,FIRST_NAME,LAST_NAME,JOB_TITLE
INTO f_emp_id,f_first_name,f_last_name,f_job_title
FROM EMPLOYEES,JOBS,DEPARTMENT
WHERE DEPARTMENT.DEPARTMENT_ID = EMPLOYEES.DEPARTMENT_ID
AND JOBS.JOB_ID = EMPLOYEES.JOB_ID
AND EMPLOYEES.DEPARTMENT_ID = f_dept_id;
RETURN TRUE;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
DBMS_OUTPUT.PUT_LINE('Employee not found');
RETURN FALSE;
END fn_emps_per_dept_jc450912;

Function FN_EMPS_PER_DEPT_JC450912 compiled
DECLARE
f_dept_id NUMBER;
f_emp_id NUMBER;
f_first_name VARCHAR(30) ;
f_last_name VARCHAR(30) ;
f_job_title VARCHAR(30);
f_return BOOLEAN;
BEGIN
f_dept_id := 1;
f_return := fn_emps_per_dept_jc450912(f_dept_id,f_emp_id,f_first_name,f_last_name,f_job_title);
DBMS_OUTPUT.PUT_LINE('Employee_ID: ' || f_emp_id);
DBMS_OUTPUT.PUT_LINE('First Name: ' || f_first_name);
DBMS_OUTPUT.PUT_LINE('Last Name: ' || f_last_name);
DBMS_OUTPUT.PUT_LINE('Job: ' || f_job_title);
END;
我得到以下错误:

Error report -
ORA-01422: exact fetch returns more than requested number of rows
ORA-06512: at "SYSTEM.FN_EMPS_PER_DEPT_JC450912", line 5
ORA-06512: at line 10
01422. 00000 -  "exact fetch returns more than requested number of rows"
*Cause:    The number specified in exact fetch is less than the rows returned.
*Action:   Rewrite the query or change number of rows requested

我需要执行体的解决方案代码来修复此错误。

首先,请使用现代连接语法(自92年以来的ANSI标准!)

因此,您的选择应该是:

SELECT EMPLOYEE_ID,FIRST_NAME,LAST_NAME,JOB_TITLE
INTO f_emp_id,f_first_name,f_last_name,f_job_title
FROM EMPLOYEES INNER JOIN JOBS ON JOBS.JOB_ID = EMPLOYEES.JOB_ID
INNER JOIN DEPARTMENT ON DEPARTMENT.DEPARTMENT_ID = EMPLOYEES.DEPARTMENT_ID
WHERE EMPLOYEES.DEPARTMENT_ID = f_dept_id;
接下来,当您遇到这样的问题时,您应该在查询窗口中运行查询,如下所示:

SELECT EMPLOYEE_ID,FIRST_NAME,LAST_NAME,JOB_TITLE
FROM EMPLOYEES INNER JOIN JOBS ON JOBS.JOB_ID = EMPLOYEES.JOB_ID
INNER JOIN DEPARTMENT ON DEPARTMENT.DEPARTMENT_ID = EMPLOYEES.DEPARTMENT_ID
WHERE EMPLOYEES.DEPARTMENT_ID = 1;
这将揭示问题的原因,因为输出如下所示

EMPLOYEE_ID FIRST_NAME           LAST_NAME                 JOB_TITLE                         
----------- -------------------- ------------------------- -----------------------------------
          1 Tony                 Starc                     IT Administrator                   
          2 Bruce                Wayne                     IT Administrator                   
          3 Larry                Ellison                   IT Administrator                   

即field employees.department\u id不是唯一的。因此,在执行时,存储过程试图在单个变量中放入多个值。这是它无法做到的,因此出现了错误。该过程编译正常,因为在编译时,该过程可能不知道它将被传递一个参数,该参数会导致结果集中出现多个记录。

首先,请使用现代联接语法(自92年以来的ANSI标准!)

因此,您的选择应该是:

SELECT EMPLOYEE_ID,FIRST_NAME,LAST_NAME,JOB_TITLE
INTO f_emp_id,f_first_name,f_last_name,f_job_title
FROM EMPLOYEES INNER JOIN JOBS ON JOBS.JOB_ID = EMPLOYEES.JOB_ID
INNER JOIN DEPARTMENT ON DEPARTMENT.DEPARTMENT_ID = EMPLOYEES.DEPARTMENT_ID
WHERE EMPLOYEES.DEPARTMENT_ID = f_dept_id;
接下来,当您遇到这样的问题时,您应该在查询窗口中运行查询,如下所示:

SELECT EMPLOYEE_ID,FIRST_NAME,LAST_NAME,JOB_TITLE
FROM EMPLOYEES INNER JOIN JOBS ON JOBS.JOB_ID = EMPLOYEES.JOB_ID
INNER JOIN DEPARTMENT ON DEPARTMENT.DEPARTMENT_ID = EMPLOYEES.DEPARTMENT_ID
WHERE EMPLOYEES.DEPARTMENT_ID = 1;
这将揭示问题的原因,因为输出如下所示

EMPLOYEE_ID FIRST_NAME           LAST_NAME                 JOB_TITLE                         
----------- -------------------- ------------------------- -----------------------------------
          1 Tony                 Starc                     IT Administrator                   
          2 Bruce                Wayne                     IT Administrator                   
          3 Larry                Ellison                   IT Administrator                   


即field employees.department\u id不是唯一的。因此,在执行时,存储过程试图在单个变量中放入多个值。这是它无法做到的,因此出现了错误。该过程编译正常,因为在编译时,该过程可能不知道将向其传递一个参数,该参数将在结果集中产生多条记录。

您的上一次插入
insert INTO EMPLOYEES(EMPLOYEES…_DATE('15/1/2013','DD/MM/yyyyy')
不完整,它会导致解析错误
SQL错误:ORA-00917:缺少逗号
我已经编辑并修复了该错误。但是,我正在寻找执行体的解决方案代码。这是我唯一需要修复的问题。函数已成功创建。但是,我仍然坚持执行语法。如果您能够提供执行部分的解决方案代码。实际上,您还没有完全修复它-超人仍然缺少一个工作ID、工资和部门ID软件测试并没有在成功编译时停止。您发现的是一个。您最后一次插入
插入员工(员工……截至日期('15/1/2013','DD/MM/YYYY'))
不完整,它会导致解析错误
SQL错误:ORA-00917:缺少逗号
我已经编辑并修复了该错误。但是,我正在寻找执行体的解决方案代码。这是我唯一需要修复的问题。函数已成功创建。但是,我仍然坚持执行语法。如果您能够提供执行部分的解决方案代码。实际上你还没有完全修复它-超人仍然缺少一个工作ID、薪水和部门ID软件测试并没有在成功编译时停止。你发现的是一个。我重新编辑并添加了克拉克·肯特(超人)的工作ID和薪水.另一方面,分配问题要求我创建一个函数,以部门id作为输入参数,其他选定列作为输出参数。我只是停留在执行部分。如果您只提供执行部分的解决方案,那将非常有用。请阅读我的回答。鉴于您的数据,没有解决方案我最好的猜测是您的分配错误。输入参数应该是employee\u id(而不是department\u id),或者您应该有一个作为记录集的输出参数(使用sys\u refcursor)。我删除了部门id,并将员工id作为输入参数,然后我应用了我的函数执行逻辑,结果是输入了有效的员工id号,输入无效的员工id时出错。当我使用员工id作为输入参数时,它工作得很好。但是,当我输入de时partment id作为获取员工详细信息的输入参数,然后显示错误。不应该这样做,因为我已经指定了EMPLOYEES.DEPARTMENT\u id=f\u dept\u id。这对我来说很奇怪。@learningIT DEPARTMENT\u id在EMPLOYEES表中不是唯一的。它是部门的外键,在该表中是唯一的。指定EMPLOYEES.dept的位置partment_id=f_dept_id因此不会生成一个结果集。因此,您的错误。我能说得更清楚些吗?我很高兴。请单击答案旁边的勾号,将问题标记为已回答。它应该变为绿色!我已重新编辑并添加了克拉克·肯特(超人)的工作id和工资.另一方面,分配问题要求我创建一个函数,以部门id作为输入参数,其他选定列作为输出参数。我只是停留在执行部分。如果您只提供执行部分的解决方案,那将非常有用。请阅读我的回答。鉴于您的数据,没有解决方案ion。我最好的猜测是您的分配错误。输入参数应该是employee_id(而不是department_id),或者您应该有一个作为记录集的单个输出参数(使用sys_refcursor)。我已经删除了department id并将employee id作为输入参数,然后应用了我的函数