我们可以在一个 PL/SQL 块中使用多个函数吗

Posted

技术标签:

【中文标题】我们可以在一个 PL/SQL 块中使用多个函数吗【英文标题】:can we use more than one function inside one PL/SQL Block 【发布时间】:2016-01-31 09:53:30 【问题描述】:
DECLARE
     avg_sal number(8,2);
     c number(8);
     total number(8,2);
     at number(8);
     a number(8);
     rt number(8);
     r number(8);
     y number(8);
     yr number(8);
     c number(8);
     ch number(8);
     FUNCTION cmd_int(amt number,rate number,intrest number)
     RETURN number
     IS
     cint number(8,2);
     BEGIN
     END;

     FUNCTION smp_int(amt number,rate number,intrest number)
     RETURN number
     IS
     sint number(8,2);
     BEGIN
         sint:=(amt*rate*intrest)/100;
         return total/c;
     END;
BEGIN
     dbms_output.put_line('Enter amount :'||:a);
     at:=:a;
     dbms_output.put_line('Enter rate :'||:r);
     rt:=r;
     dbms_output.put_line('Enter year :'||:y);
     yr:=y;
     dbms_output.put_line('1 Compound Intrest');
     dbms_output.put_line('2 Simple Intrest');
     dbms_output.put_line('Enter your choice :'||:c);
     ch:=c;
     CASE 
     WHEN ch:=1 THEN 
        ci:=cmd_int(at,rt,yr);
        dbms_output.put_line('Compound Intrest :'||ci);
     WHEN ch:=2 THEN
        si:=smp_int(at,rt,yr);
        dbms_output.put_line('Simple Intrest :'||si);
END;

以上是我要执行的代码,有两个函数 cmd_int 和 smp_int 那么我可以在一个 PL/SQL 块中执行多个函数吗?谢谢!

基本上,当我的选择是 1 时,我想执行第一部分,当我的选择是 2 时,我想执行第二部分。

【问题讨论】:

是的 - 为什么你认为你不能?您确实有一个 mostake,但这与拥有或调用两个函数无关。向我们展示您遇到的错误如何? @AlexPoole 确定! ORA-06550:第 5 行,第 6 列:PLS-00103:在预期以下情况之一时遇到符号“AT”:这是错误。 我现在也在我的回答中解决了这个问题。为什么您认为该错误与功能有关?此外,PL/SQL 的设计不是交互式的,即使在 SQL Developer 中,您对绑定变量的提示也不太可能正常工作 - 在看到 dbms_output 'prompts' 之前,您会被要求输入值。客户端应将值提供给块。 @AlexPoole 是的,你是真的错误与功能无关,但你能解决错误吗?因为我无法理解错误 【参考方案1】:

是的,您可以定义和调用任意数量的函数和过程(以及子块 - 最多 a limit)。如果你不能,PL/SQL 的功能就会被削弱。

但其余代码必须有效。你是missing an end case:

      ...
     CASE 
     WHEN ch:=1 THEN 
        ci:=cmd_int(at,rt,yr);
        dbms_output.put_line('Compound Intrest :'||ci);
     WHEN ch:=2 THEN
        si:=smp_int(at,rt,yr);
        dbms_output.put_line('Simple Intrest :'||si);
     END CASE;
END;

AT 是a reserved word in PL/SQL,因此您不能拥有具有该名称的变量,您需要更改它。

您似乎还混淆了 PL/SQL 局部变量(例如 r)和绑定变量(:r),并且您试图在块和用户之间进行交互,而 PL/SQL 不是专为。一旦 PL/SQL 块有效,您的客户端要么会抱怨并非所有变量都已绑定,要么会在执行块之前提示所有变量,而您只会看到来自 @ 的“提示”字符串987654329@ 块执行之后。

您的应用程序或客户端需要收集 PL/SQL 块之外的所有值; Michael Schaefers 展示了 SQL Developer 或 SQL*Plus 的常用方法。如果这是你的任务的一部分,你仍然可以将它与 PL/SQL 块结合起来。

【讨论】:

ORA-06550:第 5 行,第 6 列:PLS-00103:在预期以下情况之一时遇到符号“AT”:这是我进行更改后遇到的错误【参考方案2】:

从技术上回答标题的问题:是的,您可以在 PL/SQL 块中使用多个函数,如以下示例代码所示:

set serveroutput on;

DECLARE
     FUNCTION cmd_int(amt number,rate number,intrest number)
     RETURN number
     IS
     cint number(8,2);
     BEGIN
      return 4;
     END;

     FUNCTION smp_int(amt number,rate number,intrest number)
     RETURN number
     IS
     sint number(8,2);
     BEGIN
         return 5;
     END;
BEGIN
     dbms_output.put_line('Result 1: ' || cmd_int(1,2,3));
     dbms_output.put_line('Result 2: ' || smp_int(1,2,3));
END;
/

执行这个块产生

Result 1: 4
Result 2: 5

现在解决您的问题:

我建议您通过CREATE OR REPLACE FUNCTION ... 创建两个单独的函数cmd_intsmp_int,它们可以满足您的需求。由于这两个在相同的逻辑上下文中使用,您还可以创建一个包 CREATE PACKAGE INTEREST 并在此包中定义这两个函数。

然后,要求用户输入并实际使用功能,我建议您坚持使用ACCEPT 命令的 sqlplus 脚本或处理客户端应用程序中的所有内容(如果有的话)。

请参阅 CREATE FUNCTION、CREATE PACKAGE 和 sqlplus ACCEPT 上的 Oracle 文档

sqlplus 脚本的基本思想是

SET SERVEROUTPUT ON;

ACCEPT a NUMBER PROMPT 'Enter amount: ';
ACCEPT r NUMBER PROMPT 'Enter rate: ';
ACCEPT y NUMBER PROMPT 'Enter year: ';
ACCEPT c NUMBER PROMPT '1 Compount Interest, 2 Simple Interest: ';

SELECT CASE WHEN &&c = 1 THEN cmd_int(a,r,y) ELSE smp_int(a,r,y) END AS Interest FROM DUAL;

更多关于使用sqlplus的信息可以在here找到

【讨论】:

【参考方案3】:

是的。您可以在 pl/sql 块中定义更多的函数和过程。

【讨论】:

以上是关于我们可以在一个 PL/SQL 块中使用多个函数吗的主要内容,如果未能解决你的问题,请参考以下文章

可以在 PL/SQL 函数中使用正则表达式吗?

是否可以在 PL/SQL 开发人员测试窗口的“声明”块中声明子过程?

如何在匿名 PL/SQL 块中自动显示所有 SQL 语句的输出

在多个 pl sql 块上使用条件

打印 Oracle Pl/sql 光标

PL/SQL开发中动态SQL的使用方法