だから私はこれに対する解決策を見たと思いますが、それらはすべて非常に複雑なクエリです。参考までにOracle11gを使用しています。
私が持っているのは、単純な1対多の結合であり、うまく機能しますが、多くは必要ありません。左側のテーブル(1つ)が、結合条件を満たす任意の1行を結合するだけです...多くの行はありません。
クエリはカウントされるロールアップにあるため、これを行う必要があります。通常の左結合を実行すると、5行が取得されますが、1行しか取得されません。
したがって、データの例は次のとおりです。
TABLE 1:
-------------
TICKET_ID ASSIGNMENT
5 team1
6 team2
TABLE 2:
-------------
MANAGER_NAME ASSIGNMENT_GROUP USER
joe team1 sally
joe team1 stephen
joe team1 louis
harry team2 ted
harry team2 thelma
私がする必要があるのは、ASSIGNMENT = ASSIGNMENT_GROUPでこれら2つのテーブルを結合することですが、返される行は1つだけです。
左結合を実行すると、左結合の性質である3つの行が返されます。
Oracleが行番号(パーティション化)をサポートしている場合は、行が1に等しい場所を選択するサブクエリを作成できます。
SELECT * FROM table1
LEFT JOIN
(SELECT *
FROM (SELECT *,
ROW_NUMBER()
OVER(PARTITION BY assignmentgroup ORDER BY assignmentgroup) AS Seq
FROM table2) a
WHERE Seq = 1) v
ON assignmet = v.assignmentgroup
あなたはこのようなことをすることができます。
SELECT t1.ticket_id,
t1.assignment,
t2.manager_name,
t2.user
FROM table1 t1
LEFT OUTER JOIN (SELECT manager_name,
assignment_group,
user,
row_number() over (partition by assignment_group
--order by <<something>>
) rnk
FROM table2) t2
ON ( t1.assignment = t2.assignment_group
AND t2.rnk = 1 )
これにより、table2
のデータがassignment_group
で分割され、任意にランク付けされて、assignment_group
ごとに任意の1行がプルされます。どの行が返されるかを気にする場合(または返される行を決定論的にしたい場合)、分析関数にORDER BY
句を追加できます。
Oracleでは、1つの結果が必要な場合は、 ROWNUM
ステートメントを使用して、クエリの最初のN個の値を取得できます。例:
SELECT *
FROM TABLEX
WHERE
ROWNUM = 1 --gets the first value of the result
この単一のクエリの問題は、Oracleがデータを同じ順序で返すことは決してないということです。したがって、rownumを使用する前にデータを順序付けする必要があります。
SELECT *
FROM
(SELECT * FROM TABLEX ORDER BY COL1)
WHERE
ROWNUM = 1
あなたの場合、必要な結果は1つだけのように見えるので、クエリは次のようになります。
SELECT *
FROM
TABLE1 T1
LEFT JOIN
(SELECT *
FROM TABLE2 T2 WHERE T1.ASSIGNMENT = T2.ASSIGNMENT_GROUP
AND
ROWNUM = 1) T3 ON T1.ASSIGNMENT = T3.ASSIGNMENT_GROUP
必要なのは、GROUP BY
フィールドでASSIGNMENT_GROUP
を使用することだと思います。
MySQLでは、割り当てごとにグループ化するだけで完了できます。 Oracleはより厳密であり、3つの行のどの値を選択するかを(未定義の方法で)選択することを拒否します。つまり、返されるすべての列はGROUP BYの一部であるか、集計関数(COUNT、MIN、MAX ...)の対象である必要があります。
もちろん、気にせず、返された列でいくつかの集計関数を使用することを選択できます。
select TICKET_ID, ASSIGNMENT, MAX(MANAGER_NAME), MAX(USER)
from T1
left join T2 on T1.ASSIGNMENT=T2.ASSIGNMENT_GROUP
group by TICKET_ID, ASSIGNMENT
そうすれば、そもそもJOINが必要だと真剣に疑うでしょう。
MySQLは、列のグループ値の文字列連結が必要な場合(人間はしばしばそのように)、GROUP_CONCATにも役立ちますが、Oracleの場合は 驚くほど複雑 です。
すでに提案されているようにサブクエリを使用することはオプションです、 ここを見てください 例として。また、一番上の行を選択する前にサブクエリを並べ替えることもできます。