1.介绍下需求:
有两个表,结构相同,ID(主键) CARDASN(卡号) COUNT(记数)TIME(入库时间)
表A  ID      CARDASN      COUNT      TIME 
      1          001            1           08-04-05 09:09;09 
      2          001            2           08-04-06 09:09:08 
      3          002            1           08-03-07 14:11:01 
表B  ID      CARDASN       COUNT     TIME 
      1          001            4           08-04-05 10:11:54 
      2          002            3           08-03-09 06:11:19 例如 找断号 结果应该是 
     ID     START    END       
     1         3        3 
     2         1        3    
START 为断号的开始号   END 为断号的结束号 2.我这有个查询语句:
select * from (select CARDASN, COUNT+1 st, lead(COUNT-1) over (partition by CARDASNorder by COUNT) ed 
  from ( 
        select tva.CARDASN, tva.TIME , tva.COUNT from tvalidtr tva where tva.TIME > sysdate - 6 and   
        tva.TIME < sysdate-3 
  union all
        select tin.CARDASN, tin.TIME , tin.COUNT from tinvalidtr tin where tin.TIME > sysdate -6 and  
        tin.TIME < sysdate-3)) o
where ed-st >0 这样查出的结果不对,只是分别查出了两个表的断号,再把这些记录放到一起显示出来。
请高手指点如何改进。3.有人提出用存储过程来做,不知道这样的想法能否实现:
(1)首先从 tvalidtr tinvalidtr 两个表中查处所有记录放到一个虚拟的表中
(2)再从这个虚拟的表中查出断号的情况。在线求解!!!
 

解决方案 »

  1.   

    什麽是斷號?
    還有:
    sysdate-3: 2008/05/03 11:19:38
    sysdate-6: 2008/04/30 11:20:15
    這樣的話就沒有滿足條件的數據了,所以你的時間應該在確定一下
      

  2.   


    时间是我举例子写的,我测试的时候是写的between sysdate-10000  and  sysdate
      

  3.   


    哦,找的是每个cardasn的断号,例如找卡号为001的断号,从两个表中找出它的COUNT连续的数结果为:ID   CARDASN   START   END
    1        001       3     3  
      

  4.   


    断号是什么意思大家都清楚,只是楼主没说明白要对那个字段求断号
    表中的ID不存在断号,CARDASN也不存在断号,COUNT是记数不会对它吧,
    你求断号与TIME(入库时间)有什么关系?总之,不明白你的问题
      

  5.   

    START   END 字段是怎么求的?
      

  6.   


    START 是断号开始的数字 , END 是断号结束的数字 对应我写的SQL 就是 ST 和 ED
      

  7.   


    那么,     ID     START    END        
              2         1        3   
    又怎么解释?  
      

  8.   

    --表temp(CARDASN,start,end)中为断号
    n_start number;
    n_end   number;
    n_loop  number;
    CURSOR c_cursor IS   --有断号的
     select CARDASN,max(COUNT) maxCount,min(COUNT) minCount,count(*) num
      from (
            select CARDASN,COUNT from tvalidtr
            union
            select CARDASN,COUNT from tinvalidtr 
           )
     group by CARDASN
     having max(COUNT) <> count(*);for t_cursor in c_cursor loop
      n_loop := 1;
      n_end := -1;
      --小的数缺
      if n_loop < t_cursor.minCount then
        insert into temp(CARDASN,start,end)
          select t_cursor.CARDASN,n_loop,t_cursor.minCount -1;
        n_loop := t_cursor.minCount + 1;
      end if;  --其它数缺
      while n_loop <= t_cursor.maxCount Loop
        if (select count(*) from (
            select CARDASN,COUNT from tvalidtr
            union
            select CARDASN,COUNT from tinvalidtr) t
            where CARDASN = t_cursor.CARDASN and n_loop = t_cursor.COUNT) =0 then
          if (n_end == -1) then
            n_start := n_loop;
            n_end := n_loop;
          else
       n_end := n_loop;
          end if;
        else   --不缺
          if (n_end <> -1) then
            insert into temp(CARDASN,start,end)
                select t_cursor.CARDASN,n_start,n_end;
            n_end := -1;
          end if
        end if;
        n_loop := n_loop + 1;
      end loop;  
    end for;
      

  9.   

      ID     START    END         
      2         1        3    
    又怎么解释?  
      

  10.   


    ID 相当于rownum 。告诉你查出了多少条记录  
      

  11.   

    这个如果是002的断号貌似应该是
      ID     START    END          
      2         2        2
    吧?lz说下 
      

  12.   


    对 我写错了
    我想查每一个卡号(cardasn),它的count出现断号的情况!
    查出的结果应该为:
    rownum     cardasn    start    end
        1           001        3       3
        2           002        2       2
      

  13.   

    久等了。
    首先説明一下,我找的斷點是兩個表中count的最小值和最大值之間的,這點要注意。要是想從1或0開始的話,也可以,詳細見程序如下:-----------------------------------
    CREATE OR REPLACE procedure duan is
    begin
    declare
    i number :=0;
    n_st number := 0;   -- 斷點開始
    n_ed number := 0;   -- 斷點結束
    temp number;        --保存殘缺的數
    cursor cur2_duan is
     select
     CARDASN,
     min(count) as min_cnt,
     max(count) as max_cnt,
     count(distinct count) as cnt
     from
     (
     select a.CARDASN,a.count from a
     union
     select b.CARDASN,b.count from b
     )
     group by CARDASN
     having count(distinct count) < (max(count)- min(count)+1) --斷點介於最小值和最大值之間,要想從1或0開始,將 min(count)改爲 1或0
     order by CARDASN
     ;
    r2_duan cur2_duan%rowtype;begin
     for r2_duan in cur2_duan loop
     exit when cur2_duan%notfound;
              n_st := 9999;  -- 模擬最大值,具體可以調試
              n_ed := -9999; -- 模擬最小值,具體可以調試
     for t in r2_duan.min_cnt..r2_duan.max_cnt loop --斷點介於最小值和最大值之間,要想從1或0開始,將 r2_duan.min_cnt 改爲 1或0
      begin
      select t into temp
      from dual
      where  t not in
       (
       select a.count from a where a.CARDASN = r2_duan.CARDASN
       union
       select b.count from b where b.CARDASN = r2_duan.CARDASN
       );
      exception when no_data_found then
       temp := null;
      end;
      if temp is not null then
       if temp < n_st then
        n_st := temp;
       end if;
       if temp >n_ed then
        n_ed := temp;
       end if;
      end if;
     end loop;
     dbms_output.put_line(r2_duan.CARDASN || ':' || n_st || ' ' || n_ed); i:=i+1;
            insert into t_duan values(i, r2_duan.CARDASN, n_st, n_ed);   --表 t_duan 保存結果 end loop;
      commit;
    end;
    end;
    /