查找异常 (PL/SQL)
Finding exception (PL/SQL)
我是运行Oracle中的一段代码,要求用户输入路线类型,然后程序会根据用户输入的路线,获取最长和最短的路线,以及路线的数量提取的行。我需要向代码添加任何异常,并且我正在尝试考虑在这种情况下我可以添加哪种异常。我正在考虑添加一个异常,如果获取的行 <1,则会出现错误。但是,我不确定是否存在此类异常。我还需要为无效的路由类型添加一个例外。我将其表示为 IF 语句。不确定这是否算作例外。
我的代码是:
SET SERVEROUTPUT ON;
SET VERIFY OFF
DECLARE
v_type VARCHAR2 (20);
min_length NUMBER;
max_length NUMBER;
v_count NUMBER;
BEGIN
v_type := '&InsertTypeRoute';
IF v_type = 'Multi-Lane Divided' OR
v_type = 'Paved Divided' OR
v_type = 'Paved Undivided' THEN
SELECT MIN(LENGTH_KM), MAX(LENGTH_KM), COUNT(LENGTH_KM) INTO min_length, max_length, v_count
FROM TBLROUTE WHERE TYPE = v_type;
DBMS_OUTPUT.PUT_LINE('The minimum length is: ' || TO_CHAR(min_length));
DBMS_OUTPUT.PUT_LINE('The maximum length is: ' || TO_CHAR(max_length));
DBMS_OUTPUT.PUT_LINE ('Total number of '|| v_type ||' route is: ' || TO_CHAR(v_count));
ELSE
DBMS_OUTPUT.PUT_LINE ('Route type cannot be found');
END IF;
/*
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE ('Route type cannot be found'); */
END;
/
这些例外情况如何?在这种情况下它们合适吗?
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE ('Data not found');
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('This program encountered an error');
您可以使用 RAISE_APPLICATION_ERROR 过程在用户定义的范围 (-20000..-20999) 中引发特定异常,然后定义异常以便捕获它。像下面这样的东西应该可以工作:
DECLARE
SOMETHING_UNWANTED_HAPPENS BOOLEAN := TRUE;
BEGIN
IF SOMETHING_UNWANTED_HAPPENS THEN
RAISE_APPLICATION_ERROR(-20001, 'Something I didn''t want happened');
END IF;
EXCEPTION
WHEN OTHERS THEN
IF SQLCODE = -20001 THEN
DBMS_OUTPUT.PUT_LINE('My user-defined exception was raised');
-- Do whatever else you want to do to handle this exception
ELSE
DBMS_OUTPUT.PUT_LINE('Something else happened');
END IF;
END;
或者您可以声明一个 EXCEPTION 变量,用 PRAGMA EXCEPTION_INIT 初始化它,然后像使用任何其他异常一样使用它:
DECLARE
my_exception EXCEPTION;
PRAGMA EXCEPTION_INIT(my_exception, -20001);
SOMETHING_UNWANTED_HAPPENS BOOLEAN := TRUE;
BEGIN
IF SOMETHING_UNWANTED_HAPPENS THEN
RAISE my_exception;
END IF;
EXCEPTION
WHEN my_exception THEN
DBMS_OUTPUT.PUT_LINE('My user-defined exception was raised');
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('Something else happened');
END;
"Are they appropriate in this case?"
像这样处理异常被普遍认为是不好的做法。它吞下了真正的异常,所以用户知道某事失败了,但他们完全不知道是什么。
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('This program encountered an error');
在这种情况下,什么都不做比做那更好。
在您的情况下,我建议您依靠默认的 PL/SQL NO_DATA_FOUND
异常来处理无记录,并在只有一条记录时引发定制的异常。像这样:
DECLARE
v_type VARCHAR2 (20);
min_length NUMBER;
max_length NUMBER;
v_count NUMBER;
-- user-defined exception
x_single_route exception;
pragme expcetion_init(x_single_route, -20001);
BEGIN
v_type := '&InsertTypeRoute';
IF v_type = 'Multi-Lane Divided' OR
v_type = 'Paved Divided' OR
v_type = 'Paved Undivided'
THEN
SELECT MIN(LENGTH_KM), MAX(LENGTH_KM), COUNT(LENGTH_KM) INTO min_length, max_length, v_count
FROM TBLROUTE WHERE TYPE = v_type;
IF v_count > 1 THEN
DBMS_OUTPUT.PUT_LINE('The minimum length is: ' || TO_CHAR(min_length));
DBMS_OUTPUT.PUT_LINE('The maximum length is: ' || TO_CHAR(max_length));
DBMS_OUTPUT.PUT_LINE ('Total number of '|| v_type ||' route is: ' || TO_CHAR(v_count));
ELSE
raise x_single_route;
END IF;
EXCEPTION
WHEN x_single_route THEN
DBMS_OUTPUT.PUT_LINE ('Route has only one leg');
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE ('Route type cannot be found');
END;
/
一般来说,RAISE 异常是一种很好的做法:用户想知道什么时候出了问题。 (尽管这似乎是一个面向用户的程序,所以略有不同。)
...
EXCEPTION
WHEN x_single_route THEN
DBMS_OUTPUT.PUT_LINE ('Route has only one leg');
RAISE;
WHEN NO_DATA_FOUND THEN
....
如果使用WHEN_OTHERS[=17,建议添加SQLCODE和SQLERRM =] 以及 RAISE
这将告诉您到底出了什么问题。
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR MESSAGE :' || SQLCODE || ' :' || SQLERRM );
RAISE;
我是运行Oracle中的一段代码,要求用户输入路线类型,然后程序会根据用户输入的路线,获取最长和最短的路线,以及路线的数量提取的行。我需要向代码添加任何异常,并且我正在尝试考虑在这种情况下我可以添加哪种异常。我正在考虑添加一个异常,如果获取的行 <1,则会出现错误。但是,我不确定是否存在此类异常。我还需要为无效的路由类型添加一个例外。我将其表示为 IF 语句。不确定这是否算作例外。
我的代码是:
SET SERVEROUTPUT ON;
SET VERIFY OFF
DECLARE
v_type VARCHAR2 (20);
min_length NUMBER;
max_length NUMBER;
v_count NUMBER;
BEGIN
v_type := '&InsertTypeRoute';
IF v_type = 'Multi-Lane Divided' OR
v_type = 'Paved Divided' OR
v_type = 'Paved Undivided' THEN
SELECT MIN(LENGTH_KM), MAX(LENGTH_KM), COUNT(LENGTH_KM) INTO min_length, max_length, v_count
FROM TBLROUTE WHERE TYPE = v_type;
DBMS_OUTPUT.PUT_LINE('The minimum length is: ' || TO_CHAR(min_length));
DBMS_OUTPUT.PUT_LINE('The maximum length is: ' || TO_CHAR(max_length));
DBMS_OUTPUT.PUT_LINE ('Total number of '|| v_type ||' route is: ' || TO_CHAR(v_count));
ELSE
DBMS_OUTPUT.PUT_LINE ('Route type cannot be found');
END IF;
/*
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE ('Route type cannot be found'); */
END;
/
这些例外情况如何?在这种情况下它们合适吗?
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE ('Data not found');
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('This program encountered an error');
您可以使用 RAISE_APPLICATION_ERROR 过程在用户定义的范围 (-20000..-20999) 中引发特定异常,然后定义异常以便捕获它。像下面这样的东西应该可以工作:
DECLARE
SOMETHING_UNWANTED_HAPPENS BOOLEAN := TRUE;
BEGIN
IF SOMETHING_UNWANTED_HAPPENS THEN
RAISE_APPLICATION_ERROR(-20001, 'Something I didn''t want happened');
END IF;
EXCEPTION
WHEN OTHERS THEN
IF SQLCODE = -20001 THEN
DBMS_OUTPUT.PUT_LINE('My user-defined exception was raised');
-- Do whatever else you want to do to handle this exception
ELSE
DBMS_OUTPUT.PUT_LINE('Something else happened');
END IF;
END;
或者您可以声明一个 EXCEPTION 变量,用 PRAGMA EXCEPTION_INIT 初始化它,然后像使用任何其他异常一样使用它:
DECLARE
my_exception EXCEPTION;
PRAGMA EXCEPTION_INIT(my_exception, -20001);
SOMETHING_UNWANTED_HAPPENS BOOLEAN := TRUE;
BEGIN
IF SOMETHING_UNWANTED_HAPPENS THEN
RAISE my_exception;
END IF;
EXCEPTION
WHEN my_exception THEN
DBMS_OUTPUT.PUT_LINE('My user-defined exception was raised');
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('Something else happened');
END;
"Are they appropriate in this case?"
像这样处理异常被普遍认为是不好的做法。它吞下了真正的异常,所以用户知道某事失败了,但他们完全不知道是什么。
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('This program encountered an error');
在这种情况下,什么都不做比做那更好。
在您的情况下,我建议您依靠默认的 PL/SQL NO_DATA_FOUND
异常来处理无记录,并在只有一条记录时引发定制的异常。像这样:
DECLARE
v_type VARCHAR2 (20);
min_length NUMBER;
max_length NUMBER;
v_count NUMBER;
-- user-defined exception
x_single_route exception;
pragme expcetion_init(x_single_route, -20001);
BEGIN
v_type := '&InsertTypeRoute';
IF v_type = 'Multi-Lane Divided' OR
v_type = 'Paved Divided' OR
v_type = 'Paved Undivided'
THEN
SELECT MIN(LENGTH_KM), MAX(LENGTH_KM), COUNT(LENGTH_KM) INTO min_length, max_length, v_count
FROM TBLROUTE WHERE TYPE = v_type;
IF v_count > 1 THEN
DBMS_OUTPUT.PUT_LINE('The minimum length is: ' || TO_CHAR(min_length));
DBMS_OUTPUT.PUT_LINE('The maximum length is: ' || TO_CHAR(max_length));
DBMS_OUTPUT.PUT_LINE ('Total number of '|| v_type ||' route is: ' || TO_CHAR(v_count));
ELSE
raise x_single_route;
END IF;
EXCEPTION
WHEN x_single_route THEN
DBMS_OUTPUT.PUT_LINE ('Route has only one leg');
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE ('Route type cannot be found');
END;
/
一般来说,RAISE 异常是一种很好的做法:用户想知道什么时候出了问题。 (尽管这似乎是一个面向用户的程序,所以略有不同。)
...
EXCEPTION
WHEN x_single_route THEN
DBMS_OUTPUT.PUT_LINE ('Route has only one leg');
RAISE;
WHEN NO_DATA_FOUND THEN
....
如果使用WHEN_OTHERS[=17,建议添加SQLCODE和SQLERRM =] 以及 RAISE 这将告诉您到底出了什么问题。
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR MESSAGE :' || SQLCODE || ' :' || SQLERRM );
RAISE;