1

5列を含むテーブルがあります。最初の列には ID が含まれ、2 つの列には値が 0 または 1 の ID のパラメーターが含まれ、3 番目の列には出力として必要なパラメーターが含まれ、最後の列には日付が含まれます。パラメータが異なる複数の行に同じ ID が表示される場合があります。

ID        parameter1      parameter2        parameter3       date

001       0               1                 A                01.01.2010
001       0               1                 B                02.01.2010
001       1               0                 C                01.01.2010
001       1               1                 D                01.01.2010
002       0               1                 A                01.01.2010

の値を返したい一意の ID ごとに、どの行からこの値を返すかは、 およびparameter3の値に基づいて決定されます。parameter1parameter2

  • 両方のパラメーターが である行がある0場合、この行の値が必要です。
  • そのような行がない場合は、parameter1 が、parameter2 が である行の値が必要です01
  • そのような行がない場合は、 parameter1 が で1、 parameter2 が である行が必要です0
  • 最後に、そのような行がない場合は、両方のパラメーターが である行からの値が必要です1

必要な条件に一致する行が複数ある場合は、日付が最新の行が必要です。

たとえば、上記のテーブルの場合、IDの場合、parameter3001の値を含む 2 行目が必要です。B

これを達成するための最も効果的/最速の方法は何ですか? これまでに2つのアプローチを試しました:

select最初のものは、すべての個別の ID を選択してから、句に ID を含むステートメントを使用して個別の ID をwhereループし、必要な値を変数に格納しながら ID に一致するすべての行をループします。

foreach
    select distinct ID into i_ID from table1
        foreach
            let o_case = 5
            select case
                when parameter1 = 0 and parameter2 = 0 then 1
                when parameter1 = 0 and parameter2 = 1 then 2
                when parameter1 = 1 and parameter2 = 0 then 3
                when parameter1 = 1 and parameter2 = 1 then 4
                end, parameter3, date
                into i_case, i_p3, i_date
                from table3
                where table3.ID = i_ID

                if i_case < o_case 
                    then let o_p3, o_case, o_date = i_p3, i_case, i_date;
                    else ( if i_case = o_case and i_date > o_date
                        then let o_p3, o_date = i_p3, i_date;
                    end if;
                end if;
        end foreach;
        insert into table_output values(i_ID; o_p3);
end foreach;

2 番目のアプローチは、ID でテーブルを 4 回左結合し、左結合で上記のように parameter1 と parameter2 のさまざまな組み合わせを適用し、ネストされたnvl句を介して出力を選択することでした。

select ID, 
    nvl(t1.parameter3, 
        nvl(t2.parameter3,
            nvl(t3.parameter3,
                nvl(t4.parameter3)))) parameter3
from table1 t0
    left join table1 t1
        on t0.ID = t1.ID and t1.parameter1 = 0 and t1.parameter2 = 0
        and t1.date = (select max(date) from table1 t1a where t1a.ID = t1.ID)        
    left join table1 t2
        on t0.ID = t2.ID and t2.parameter1 = 0 and t2.parameter2 = 1
        and t2.date = (select max(date) from table1 t2a where t2a.ID = t1.ID)
    left join table1 t3
        on t0.ID = t3.ID and t3.parameter1 = 1 and t3.parameter2 = 0
        and t3.date = (select max(date) from table1 t3a where t3a.ID = t3.ID)
    left join table1 t4
        on t0.ID = t4.ID and t4.parameter1 = 1 and t4.parameter2 = 1
        and t4.date = (select max(date) from table1 t4a where t4a.ID = t4.ID)

どちらのアプローチも基本的には機能しましたが、テーブルが非常に長いため、遅すぎました。あなたは何をお勧めします?

PS: DBMS は IBM Informix 10 です。残念ながら、利用可能な機能の範囲が大幅に制限されています。

4

2 に答える 2