1

複数のクエリ (たとえば 4) を結合すると、次の結果が得られます。

結果 :

id  name    num
13  task1   0
13  task1   7102

ユニオン ステートメントに同じ ID を持つレコードが複数ある場合に、num が 0 より大きい一意のレコードのみを取得する方法。


foreach 
SELECT DISTINCT a.task_code,
                a.task_name ,
                0 AS cand_num INTO ll_task_code ,
                                   ls_task_name,
                                   ll_cand_num
FROM rmtask a,
     rmtaskstate b,
     rmstateuser c
WHERE (a.task_code = b.task_code)
  AND (b.state_code = c.state_code)
  AND (c.emp_num = al_emp_num)
  AND (al_new_flag = 0
       OR (al_new_flag = 1
           AND b.new_flag = 1))
UNION --candidate

SELECT DISTINCT a.task_code,
                a.task_name ,
                cand.emp_num
FROM rmtask a,
     rmtaskstate b,
     rmstateuser c ,
     rmcandidate cand
WHERE (a.task_code = b.task_code)
  AND (b.state_code = c.state_code)
  AND (c.emp_num = cand.emp_num)
  AND (al_new_flag = 0
       OR (al_new_flag = 1
           AND b.new_flag = 1))
  AND (cand.task_code = b.task_code)
  AND (cand.emp_num_candidate = al_emp_num)
  AND (cand.from_date <= DATE(CURRENT))
  AND (cand.to_date >= DATE(CURRENT)
       OR cand.to_date IS NULL)
UNION
SELECT DISTINCT a.task_code,
                a.task_name ,
                0 AS cand_num
FROM rmtask a,
     rmtaskstate b,
     rmstategroup c
WHERE (a.task_code = b.task_code) )
UNION --candidate

SELECT DISTINCT a.task_code,
                a.task_name ,
                cand.emp_num
FROM rmtask a,
     rmtaskstate b,
     rmstategroup c ,
     rmcandidate cand
WHERE (a.task_code = b.task_code)
  AND (b.state_code= c.state_code)
  AND (al_new_flag = 0
       OR (al_new_flag = 1
           AND b.new_flag = 1))
  AND (((c.group_type = 0))
       OR ((c.group_type = 1)
           AND (c.group_code =
                  (SELECT x.degree_code
                   FROM hr_l x
                   WHERE x.emp_num = cand.emp_num
                     AND x.degree_date =
                       (SELECT max(xx.degree_date)
                        FROM hm xx
                        WHERE xx.emp_num = x.emp_num))))
       OR ((c.group_type = 2)
           AND (c.group_code =
                  (SELECT y.title_code
                   FROM ht y
                   WHERE y.emp_num = cand.emp_num
                     AND y.title_date =
                       (SELECT max(yy.title_date)
                        FROM ht yy
                        WHERE yy.emp_num = y.emp_num))))
       OR ((c.group_type = 3)
           AND (1 = r_boss(cand.emp_num)))
       OR ((c.group_type = 4)
           AND (0 <
                  (SELECT count(*)
                   FROM ht x
                   WHERE x.emp_num = cand.emp_num
                     AND x.perm_flag = 1)))
       OR ((c.group_type = 5)
           AND (0 <
                  (SELECT count(*)
                   FROM hm x
                   WHERE x.emp_num = cand.emp_num
                     AND x.vac_flag = 1)))
       OR ((c.group_type = 6)
           AND (0 <
                  (SELECT count(*)
                   FROM hm x
                   WHERE x.emp_num = cand.emp_num
                     AND x.mission_flag = 1))))
  AND (cand.task_code = b.task_code)
  AND (cand.emp_num_candidate = al_emp_num)
  AND (cand.from_date <= DATE(CURRENT))
  AND (cand.to_date >= DATE(CURRENT)
       OR cand.to_date IS NULL) RETURN ll_task_code ,
                                       ls_task_name,
                                       ll_cand_num WITH resume ;
end foreach;
4

2 に答える 2

1
  1. FROM句でコンマリストの代わりにJOIN表記を使用します。
  2. ラリーでは、答えを出すためにすべてのクエリを確認する必要はありません。組合には2つの部分で十分です。
  3. 使用しているInformixのバージョンについて言及していないため、違いが生じる可能性があります。
  4. あなたのサンプル出力があなたが書いたSQLと結びついているなら、それはより簡単でしょう。サンプル出力では、、、を使用していますが、SQLでは、、、を使用しidnameいるようです。numtask_codetask_namecand_num
  5. 特定のタスクコードとタスク名の最大候補数が必要なようです。

したがって、次のようなクエリを記述します。

SELECT u.task_code, u.task_name, MAX(u.cand_num)
  FROM (SELECT DISTINCT a.task_code, a.task_name, 0 AS cand_num
          FROM rmtask a
          JOIN rmtaskstate b ON a.task_code = b.task_code
          JOIN rmstateuser c ON b.state_code = c.state_code
         WHERE (c.emp_num = al_emp_num)
           AND (al_new_flag = 0 OR (al_new_flag = 1 AND b.new_flag = 1))
        UNION
        SELECT DISTINCT a.task_code, a.task_name, cand.emp_num
          FROM rmtask a
          JOIN rmtaskstate b ON a.task_code = b.task_code
          JOIN rmstateuser c ON b.state_code = c.state_code
          JOIN rmcandidate cand ON c.emp_num = cand.emp_num
         WHERE (al_new_flag = 0 OR (al_new_flag = 1 AND b.new_flag = 1))
           AND (cand.task_code = b.task_code)
           AND (cand.emp_num_candidate = al_emp_num)
           AND (cand.from_date <= DATE(CURRENT))
           AND (cand.to_date >= DATE(CURRENT) OR cand.to_date IS NULL)
       ) AS u
 GROUP BY u.task_code, u.task_name;

明らかに、サブクエリ内に他の代替UNIONブランチを追加できます。

于 2013-02-01T06:08:35.083 に答える
1

を含む行num != 0が 1 つしかない場合、または結果が 1 つだけ必要な場合は、既存のクエリをサブクエリに入れてGROUP BY、集計を使用することが示されます。

select id,name,MAX(num) as num
from
   (
       select id,name,num from abc
       union
       select id,name,num from def
       union
       select id,name,num from ghi
   ) as t
group by id,name
于 2013-01-31T10:47:39.500 に答える