13

各コースコードの最後に完了したコース日付と、各従業員の全体的な最後に完了したコースコードを含む結果テーブルを作成しようとしています。以下は私の質問です:

SELECT employee_number,
       MAX(course_completion_date) 
           OVER (PARTITION BY course_code) AS max_course_date,
       MAX(course_completion_date) AS max_date
FROM employee_course_completion
WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
GROUP BY employee_number

このクエリは次のエラーを生成します。

3504 : Selected non-aggregate values must be part of the associated group

MAX()OVER(PARTITION BY ...)行を削除すると、クエリは正常に実行されるため、問題をその行に切り分けましたが、これらのフォーラムとインターネットを検索した後、自分が何をしているのかわかりません。 m間違っている。誰か助けてもらえますか?

4

5 に答える 5

6

Poniesがコメントで述べているように、OLAP関数と集計関数を混在させることはできません。

おそらく、各従業員の最終完了日を取得し、それを3つの対象コースのそれぞれの最終完了日を含むデータセットに結合する方が簡単です。

これはテストされていないアイデアであり、うまくいけば正しい道をたどるはずです。

  SELECT employee_number,
         course_code,
         MAX(course_completion_date) AS max_date,
         lcc.LAST_COURSE_COMPLETED
    FROM employee_course_completion ecc
         LEFT JOIN (
             SELECT employee_number,
                    MAX(course_completion_date) AS LAST_COURSE_COMPLETED
               FROM employee_course_completion
              WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
         ) lcc
         ON lcc.employee_number = ecc.employee_number
   WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
GROUP BY employee_number, course_code, lcc.LAST_COURSE_COMPLETED
于 2010-06-22T19:58:22.557 に答える
5

論理的には、OLAP関数はGROUP BY / HAVINGの後に計算されるため、GROUPBYの列または集計関数のある列にのみアクセスできます。以下は奇妙に見えますが、標準SQLです。

SELECT employee_number,
       MAX(MAX(course_completion_date)) 
           OVER (PARTITION BY course_code) AS max_course_date,
       MAX(course_completion_date) AS max_date
FROM employee_course_completion
WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
GROUP BY employee_number, course_code

また、Teradataではエイリアスの再利用が許可されているため、これも機能します。

SELECT employee_number,
       MAX(max_date) 
           OVER (PARTITION BY course_code) AS max_course_date,
       MAX(course_completion_date) AS max_date
FROM employee_course_completion
WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
GROUP BY employee_number, course_code
于 2014-12-30T11:22:14.333 に答える
1

これは非常に古い質問ですが、他の誰かから似たような質問がありました。

私はTeraDataを持っていませんが、次のことはできませんか?

SELECT employee_number,
       course_code,
       MAX(course_completion_date)                                     AS max_course_date,
       MAX(course_completion_date) OVER (PARTITION BY employee_number) AS max_date
FROM employee_course_completion
WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
GROUP BY employee_number, course_code

これGROUP BYで、従業員ごとにコースごとに1行が確保されます。MAX()これは、を取得するためにストレートが必要なことを意味しますmax_course_date

以前GROUP BYは、従業員ごとに1つの行を提供し、その1つの行(コースごとMAX() OVER()に1つ)に対して複数の結果を提供しようとしていました。

代わりに、従業員全体のOVER()を取得するための句が必要になります。MAX()これは、個々の行が1つの回答しか得られないため(サブセットではなくスーパーセットから派生しているため)、正当なものになりました。また、同じ理由で、OVER()句は、句で定義されている有効なスカラー値を参照するようになりましたGROUP BYemployee_number


おそらく、これを簡単に言うと、aggregatewith句は、サブセットではなく、OVER()のスーパーセットでなければならないということです。GROUP BY

GROUP BY必要な行を表すレベルでクエリを作成OVER()し、より高いレベルで集計する場合は句を指定します。

于 2012-04-27T23:37:28.653 に答える
0

これはずっと前のことですが、これでうまくいくと思います。

SELECT employee_number, Row_Number()  
   OVER (PARTITION BY course_code ORDER BY course_completion_date DESC ) as rownum
FROM employee_course_completion
WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
   AND rownum = 1

日付が同じである場合に最後のIDを取得する場合は、主キーがIdであると想定してこれを使用できます。

SELECT employee_number, Row_Number()  
   OVER (PARTITION BY course_code ORDER BY course_completion_date DESC, Id Desc) as rownum    FROM employee_course_completion
WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
   AND rownum = 1
于 2019-01-25T10:23:38.807 に答える
-1
SELECT employee_number, course_code, MAX(course_completion_date) AS max_date
FROM employee_course_completion
WHERE course_code IN ('M910303', 'M91301R', 'M91301P')
GROUP BY employee_number, course_code
于 2019-03-12T02:56:51.183 に答える