oracle-是否可以从PL / SQL块输出SELECT语句?
如何获得PL / SQL块以输出SELECT语句的结果,就像执行普通的SELECT一样?
例如如何做一个SELECT像这样:
SELECT foo, bar FROM foobar;
提示:
BEGIN
SELECT foo, bar FROM foobar;
END;
不起作用。
11个解决方案
39 votes
这取决于您需要的结果。
如果确定只有1行,请使用隐式游标:
DECLARE
v_foo foobar.foo%TYPE;
v_bar foobar.bar%TYPE;
BEGIN
SELECT foo,bar FROM foobar INTO v_foo, v_bar;
-- Print the foo and bar values
dbms_output.put_line('foo=' || v_foo || ', bar=' || v_bar);
EXCEPTION
WHEN NO_DATA_FOUND THEN
-- No rows selected, insert your exception handler here
WHEN TOO_MANY_ROWS THEN
-- More than 1 row seleced, insert your exception handler here
END;
如果要选择多于1行,则可以使用一个显式游标:
DECLARE
CURSOR cur_foobar IS
SELECT foo, bar FROM foobar;
v_foo foobar.foo%TYPE;
v_bar foobar.bar%TYPE;
BEGIN
-- Open the cursor and loop through the records
OPEN cur_foobar;
LOOP
FETCH cur_foobar INTO v_foo, v_bar;
EXIT WHEN cur_foobar%NOTFOUND;
-- Print the foo and bar values
dbms_output.put_line('foo=' || v_foo || ', bar=' || v_bar);
END LOOP;
CLOSE cur_foobar;
END;
或使用其他类型的游标:
BEGIN
-- Open the cursor and loop through the records
FOR v_rec IN (SELECT foo, bar FROM foobar) LOOP
-- Print the foo and bar values
dbms_output.put_line('foo=' || v_rec.foo || ', bar=' || v_rec.bar);
END LOOP;
END;
Sergey Stadnik answered 2019-11-03T03:22:03Z
37 votes
您可以在Oracle 12.1或更高版本中执行此操作:
declare
rc sys_refcursor;
begin
open rc for select * from dual;
dbms_sql.return_result(rc);
end;
我没有要测试的DBVisualizer,但这应该是您的起点。
有关更多详细信息,请参见《 Oracle 12.1新功能指南》,《 Oracle Base等》中的隐式结果集。
对于较早的版本,取决于工具,您可能可以使用ref游标绑定变量,例如SQL * Plus中的以下示例:
set autoprint on
var rc refcursor
begin
open :rc for select count(*) from dual;
end;
/
PL/SQL procedure successfully completed.
COUNT(*)
----------
1
1 row selected.
William Robertson answered 2019-11-03T03:22:48Z
8 votes
来自匿名区块? 现在,我想进一步介绍一下您认为需要的情况,因为有了子查询分解子句和内联视图,很少需要在最复杂的情况下使用PL / SQL处理其他事情。
如果可以使用命名过程,请使用流水线函数。 这是从文档中提取的示例:
CREATE PACKAGE pkg1 AS
TYPE numset_t IS TABLE OF NUMBER;
FUNCTION f1(x NUMBER) RETURN numset_t PIPELINED;
END pkg1;
/
CREATE PACKAGE BODY pkg1 AS
-- FUNCTION f1 returns a collection of elements (1,2,3,... x)
FUNCTION f1(x NUMBER) RETURN numset_t PIPELINED IS
BEGIN
FOR i IN 1..x LOOP
PIPE ROW(i);
END LOOP;
RETURN;
END;
END pkg1;
/
-- pipelined function is used in FROM clause of SELECT statement
SELECT * FROM TABLE(pkg1.f1(5));
David Aldridge answered 2019-11-03T03:23:20Z
8 votes
在包中创建一个函数并返回SYS_REFCURSOR:
FUNCTION Function1 return SYS_REFCURSOR IS
l_cursor SYS_REFCURSOR;
BEGIN
open l_cursor for SELECT foo,bar FROM foobar;
return l_cursor;
END Function1;
Igor Zelaya answered 2019-11-03T03:23:45Z
4 votes
经典的“ Hello World!”块包含一个可执行部分,该部分调用DBMS_OUTPUT.PUT_LINE过程在屏幕上显示文本:
BEGIN
DBMS_OUTPUT.put_line ('Hello World!');
END;
您可以在此处结帐:[http://www.oracle.com/technetwork/issue-archive/2011/11-mar/o21plsql-242570.html]
Dinesh Katwal answered 2019-11-03T03:24:15Z
4 votes
如果要查看pl / sql中的select查询输出,则需要使用显式游标。 只要它通过循环迭代从数据集中获取记录,它将保存活动数据集并一次获取每一行,它将显示活动数据集中的所有记录。 不会以表格格式生成此数据,该结果将以纯文本格式生成。 希望这会有所帮助。 对于任何其他查询,您可能会问...。
set serveroutput on;
declare
cursor c1 is
select foo, bar from foobar;
begin
for i in c1 loop
dbms_output.put_line(i.foo || ' ' || i.bar);
end loop;
end;
Ahsan Habib answered 2019-11-03T03:24:40Z
3 votes
对于低于12c的版本,简单的答案是“否”,至少不是以SQL Server的方式完成。
您可以打印结果,可以将结果插入表格,可以从函数/过程中以游标形式返回结果,也可以从函数中返回行集-
但是您不能执行SELECT语句,而不对结果做任何事情。
SQL服务器
begin
select 1+1
select 2+2
select 3+3
end
/ *返回3个结果集* /
甲骨文
SQL> begin
2 select 1+1 from dual;
3 end;
4 /
select * from dual;
*
ERROR at line 2:
ORA-06550: line 2, column 1:
PLS-00428: an INTO clause is expected in this SELECT statement
David דודו Markovitz answered 2019-11-03T03:25:28Z
2 votes
您需要使用本机动态SQL。 另外,您不需要BEGIN-END即可运行SQL命令:
declare
l_tabname VARCHAR2(100) := 'dual';
l_val1 VARCHAR2(100):= '''foo''';
l_val2 VARCHAR2(100):= '''bar''';
l_sql VARCHAR2(1000);
begin
l_sql:= 'SELECT '||l_val1||','||l_val2||' FROM '||l_tabname;
execute immediate l_sql;
dbms_output.put_line(l_sql);
end;
/
Output:
SELECT 'foo','bar' FROM dual
Art answered 2019-11-03T03:25:52Z
2 votes
使用立即执行语句
喜欢:
declare
var1 integer;
var2 varchar2(200)
begin
execute immediate 'select emp_id,emp_name from emp'
into var1,var2;
dbms_output.put_line(var1 || var2);
end;
Vamsi Praveen Karanam answered 2019-11-03T03:26:22Z
0 votes
即使问题很旧,但我将分享完美回答问题的解决方案:
SET SERVEROUTPUT ON;
DECLARE
RC SYS_REFCURSOR;
Result1 varchar2(25);
Result2 varchar2(25);
BEGIN
OPEN RC FOR SELECT foo, bar into Result1, Result2 FROM foobar;
DBMS_SQL.RETURN_RESULT(RC);
END;
Issam El omri answered 2019-11-03T03:26:46Z
0 votes
当选择查询返回多行时,将使用游标。 因此,如果需要聚合或单个行数据,可以使用游标,而不必使用游标,例如
Create Procedure sample(id
varchar2(20))as
Select count(*) into x from table
where
Userid=id;
End ;
然后只需调用该过程
Begin
sample(20);
End
这是过程/函数的实际用法,主要是包装和存储复杂的查询或需要使用相同逻辑但不同数据进行重复操作的查询
Himanshu Ahuja answered 2019-11-03T03:27:23Z