名前の競合が発生したり、出力列を混乱させたりする場合を除いて、クエリはすでに機能します。 ( CASE 式)ソース列 結果コード> 、内容が異なります。
...
GROUP BY model.name, attempt.type, attempt.result
...
GROUP BYする必要があります あなたのCASE ソース列の代わりに式:
...
GROUP BY model.name, attempt.type
, CASE WHEN attempt.result = 0 THEN 0 ELSE 1 END
...
または、列エイリアスを指定します これは、 FROMの列名とは異なります。 リスト-または、その列が優先されます:
SELECT ...
, CASE WHEN attempt.result = 0 THEN 0 ELSE 1 END AS result1
...
GROUP BY model.name, attempt.type, result1
... SQL標準は、この点でかなり独特です。ここでマニュアルを引用する:
出力列の名前を使用して、
ORDER BYの列の値を参照できます。 およびGROUPBY句はありますが、WHEREにはありません またはHAVING句;代わりに式を書き出す必要があります。
そして:
ORDER BYの場合 式は、出力列名と入力列名の両方に一致する単純な名前、ORDER BYこれを出力列名として解釈します。 これは、GROUP BYの選択の反対です。 作る 同じ状況で。この不整合は、SQL標準と互換性があるように作成されています。
太字 強調鉱山。
これらの競合は、位置参照を使用することで回避できます。 (序数) GROUP BY およびORDERBY 、 SELECT内のアイテムを参照する 左から右にリストします。以下の解決策を参照してください。
欠点は、これが読みにくく、 SELECTでの編集に対して脆弱である可能性があることです。 リスト(それに応じて位置参照を適応させるのを忘れるかもしれません)。
しかし、あなたはしません day列を追加する必要があります GROUP BYへ 定数値( CURRENT_DATE-1 を保持している限り) 。
適切なJOIN構文と位置参照を使用して書き直し、簡略化すると、次のようになります。
SELECT m.name
, a.type
, CASE WHEN a.result = 0 THEN 0 ELSE 1 END AS result
, CURRENT_DATE - 1 AS day
, count(*) AS ct
FROM attempt a
JOIN prod_hw_id p USING (hard_id)
JOIN model m USING (model_id)
WHERE ts >= '2013-11-06 00:00:00'
AND ts < '2013-11-07 00:00:00'
GROUP BY 1,2,3
ORDER BY 1,2,3;
また、列名 timeを避けていることにも注意してください。 。これは予約語であり、識別子として使用しないでください。その上、あなたの「時間」は明らかにタイムスタンプです またはdate 、それはかなり誤解を招く恐れがあります。