算法:先吧所有的表名取出来,用“select tablename from dual union“,union的方法将重复的表名去掉SQL> set serveroutput on
SQL> declare
2 strtablename varchar2(500) :='table1,table2,table1,table3,table4,';
3 v_sql varchar2(1000);
4 v_strtable varchar2(50);
5 i1 number :=1;
6 i2 number :=1;
7 type v_cursor is ref cursor;
8 v_cursortemp v_cursor;
9 begin
10 for i in 1..length(strtablename) loop
11 i2 :=instr(strtablename,',',i1) ;
12 if i2=0 then
13 exit;
14 end if;
15 v_strtable := substr(strtablename,i1,i2-i1);
16 dbms_output.put_line('gettablename:' || v_strtable || ';');
17 i1 := i2+1;
18 if i =1 then
19 v_sql := v_sql || 'select '' ' || v_strtable || ' '' from dual';
20 else
21 v_sql := v_sql || ' union select '' ' || v_strtable || ' '' from dual
';
22 end if;
23 end loop;
24
25 open v_cursortemp for v_sql;
26 loop
27 fetch v_cursortemp into v_strtable;
28 exit when v_cursortemp%notfound;
29 dbms_output.put_line('tablename:' || v_strtable || ';');
30 end loop;
31 close v_cursortemp;
32 end;
33 /
gettablename:table1;
gettablename:table2;
gettablename:table1;
gettablename:table3;
gettablename:table4;
tablename: table1 ;
tablename: table2 ;
tablename: table3 ;
tablename: table4 ;PL/SQL procedure successfully completed.
SQL> declare
2 strtablename varchar2(500) :='table1,table2,table1,table3,table4,';
3 v_sql varchar2(1000);
4 v_strtable varchar2(50);
5 i1 number :=1;
6 i2 number :=1;
7 type v_cursor is ref cursor;
8 v_cursortemp v_cursor;
9 begin
10 for i in 1..length(strtablename) loop
11 i2 :=instr(strtablename,',',i1) ;
12 if i2=0 then
13 exit;
14 end if;
15 v_strtable := substr(strtablename,i1,i2-i1);
16 dbms_output.put_line('gettablename:' || v_strtable || ';');
17 i1 := i2+1;
18 if i =1 then
19 v_sql := v_sql || 'select '' ' || v_strtable || ' '' from dual';
20 else
21 v_sql := v_sql || ' union select '' ' || v_strtable || ' '' from dual
';
22 end if;
23 end loop;
24
25 open v_cursortemp for v_sql;
26 loop
27 fetch v_cursortemp into v_strtable;
28 exit when v_cursortemp%notfound;
29 dbms_output.put_line('tablename:' || v_strtable || ';');
30 end loop;
31 close v_cursortemp;
32 end;
33 /
gettablename:table1;
gettablename:table2;
gettablename:table1;
gettablename:table3;
gettablename:table4;
tablename: table1 ;
tablename: table2 ;
tablename: table3 ;
tablename: table4 ;PL/SQL procedure successfully completed.
oracle中的instr 函数你用过吧,用这个来实现就很方便。
设立一个for循环,循环变量i取逗号在该串中的个数。(好象也有这函数,记不太清了) 设立得到的字符串名target_string,变量的初值是‘’
这样每次循环截取串中,前的一部分:
判断:instr(target_string,该部分)>0 那么表示已存在,作下一次循环
不存在:将该部分加入target_string串中。
s1:原来的字符串
s2:要得到的字符串
s3:临时变量1。使用instr在s1中对逗号定位,取得表名,放在s3(包含逗号)中,同时,加在s2的末尾。
2。使用replace,将s1中包含的s3替换为''。
3。在从1开始,重复。最终,s2就是你想要的。
type arr_type is table of varchar(50) index by binary_integer;
arr arr_type;
str1 string(500);
str2 string(500);
i integer;
j integer;
v_count integer;
begin
str1:='table1,tableddd2,table1,table3,tablecc4,table5,tableddd2,tablecc4,table5,tableddd2';
i:=0;
--将str1分解放入数组
while str1 is not null loop
arr(i):=substr(str1,1,instr(str1,',')-1);
j:=length(arr(i));
str1:=substr(str1,j+2,length(str1));
i:=i+1;
end loop;
v_count:=i-1;
str2:='';
--取出不同的表名放入str2
for i in 0..v_count loop
if instr(arr(i),'@')=0 then
str2:=str2||','||arr(i);
for j in (i+1)..v_count loop
if arr(i)=arr(j) then
arr(j):='@'||arr(j);
end if;
end loop;
end if;
end loop;
--去掉第一个逗号
str2:=substr(str2,2,length(str2));dbms_output.put_line(str2);end testarr;
declare
v_tabname varchar2(500) := 'table1,table2,table1,table3,table4,table2,table3,,table4';
v_result varchar2(500) := ' ';
v_tmpstr varchar2(500);
v_startpos number := 1;
v_endpos number;
begin
loop
v_endpos := instr(v_tabname, ',', v_startpos);
if v_endpos = 0 then
exit;
end if;
if v_endpos > v_startpos then
v_tmpstr := trim(substr(v_tabname, v_startpos, v_endpos - v_startpos)) || ',';
if instr(v_result, v_tmpstr) = 0 then
v_result := v_result || v_tmpstr;
end if;
end if;
v_startpos := v_endpos + 1;
end loop;
v_result := rtrim(v_result, ',');
DBMS_OUTPUT.PUT_LINE('result:' || v_result);
end;
/
另:该程序在ORACLE8i上测试通过,在ORACLE8上需要将trim函数替换为ltrim(rtrim())函数的形式。附:zhaoyaongzhu的方法的确巧妙,只是太复杂了一点;
rady88可惜没有源程序,无法瞻仰其高手风范,可惜啊可惜!
CHENGXB使用两重循环……,似乎无此必要。
呵呵!小弟在此胡言,各位大侠莫要见怪!!!
================================================================CSDN 论坛助手 Ver 1.0 B0402提供下载。 改进了很多,功能完备!★ 浏览帖子速度极快![建议系统使用ie5.5以上]。 ★ 多种帖子实现界面。
★ 保存帖子到本地[html格式]★ 监视您关注帖子的回复更新。
★ 可以直接发贴、回复帖子★ 采用XML接口,可以一次性显示4页帖子,同时支持自定义每次显示帖子数量。可以浏览历史记录!
★ 支持在线检测程序升级情况,可及时获得程序更新的信息。★★ 签名 ●
可以在您的每个帖子的后面自动加上一个自己设计的签名哟。Http://www.ChinaOK.net/csdn/csdn.zip
Http://www.ChinaOK.net/csdn/csdn.rar
Http://www.ChinaOK.net/csdn/csdn.exe [自解压]