例如: 
    table1数据如下:         test1            test2            test3 
---------------------------------------------------- 
      12,3.4和5        7811;12        131415     随碟附送史蒂夫        1112          13,14,15.17       123456            8和9和10          16.17.18 test1取值范围:1;2;3;4;5;6 
test2取值范围:7;8;9;10;11;12 
test3取值范围:13;14;15;16;17 
也就是说字段内容只会出现在范围之内的序号 
怎么通过函数返回以下内容: 
        test1            test2                test3 
----------------------------------------------------------- 
      12;3;4;5        7;8;11;12        13;14;15     随碟附送史蒂夫        11;12            13;14;15;17   1;2;3;4;5;6      8;9;10            16;17;18 如果内容部存在指定的内容则返回原始内容,请Oracle高手指教

解决方案 »

  1.   

    最后一条记录的test3为什么返回16,17,18
    18不是不包含在13;14;15;16;17 中吗
      

  2.   

    create or replace function func(str in varchar2,flag in number)
    return varchar2
    as
    newstr varchar2(200);
    compare_str varchar2(20);
    temp varchar2(10);
    begin
    if str is null then return null; end if;
    if flag=1 then compare_str:=';1;2;3;4;5;6;';
      elsif flag=2 then compare_str:=';7;8;9;10;11;12;';
      elsif flag=3 then compare_str:=';13;14;15;16;17;';
      else return null;
    end if;
    for i in 1..length(str)loop
      temp:=temp||substr(str,i,1);
      if instr(compare_str,';'||temp||';')>0 then
          newstr:=newstr||temp||';';
          temp:=null;
      elsif instr(compare_str,';'||temp)>0 then
        null;
      else
        temp:=null;
      end if;
    end loop;
    if newstr is null then return str;
    else return rtrim(newstr,';');
    end if;
    end func;
    传入test1字段时,传入参数flag填1,test2对应2,test3对应3
    比如
    with table1 as(select '12;3;4;5' test1,'7;8;11;12' test2,'13;14;15 ' test3 from dual
      union all select '随碟附送史蒂夫','1112','13,14,15.17' from dual
      union all select ' 123 456','8和9  和10',' 16.17.18 ' from dual
    )
    select func(test1,1),func(test2,2),func(test3,3) from table1FUNC(TEST1,1) FUNC(TEST2,2) FUNC(TEST3,3)
    1;2;3;4;5 7;8;11;12 13;14;15
    随碟附送史蒂夫 11;12 13;14;15;17
    1;2;3;4;5;6 8;9;10 16;17
      

  3.   

    table.test1列可以实现,其他两列试完了再发SELECT NVL(
               regexp_replace(
                              regexp_replace(
                                            test1,
                                            '[^(1-6)]',
                                            ''),
                              '(\d)',
                              '\1;'
                              ),
               test1,
               )
     from table1;
      

  4.   

    上面有点小问题,改正SELECT NVL( 
              regexp_replace( 
                              regexp_replace( 
                                            test1, 
                                            '[^(1-6)]', 
                                            ''), 
                              '(\d)', 
                              '\1;' 
                              ), 
              test1
              ) 
    from table1;
      

  5.   

    table1.test2的实现方式:SELECT NVL(
               regexp_replace(
                              regexp_replace(
                                            test2,
                                            '[^(7|8|9|10|11|12)]',
                                            ''),
                              '(7|8|9|10|11|12)',
                              '\1;'
                              ),
               test2
               )
     from table1;
      

  6.   


    这样子写不好,如果有N个字段,函数还不是要定义N种FLAG!
    麻烦!
      

  7.   

    同第二列,第三列也可以实现了SELECT NVL(
               regexp_replace(
                              regexp_replace(
                                            test3,
                                            '[^(13|14|15|16|17|18)]',
                                            ''),
                              '(13|14|15|16|17|18)',
                              '\1;'
                              ),
               test3
               )
     from table1;
      

  8.   

    n个字段有n个不同的需求,只能写n个字符串
    难道有更好的办法?zcs_1的正则很厉害
    学习下
      

  9.   

    可以将flag去掉,换成传入compare_str..这样更通用些