データベースにメッセージテーブルがあり、送信者IDとメッセージタイプが含まれています(もちろん、この質問には関係のない列がさらに多くあります)。ユーザーが送信した各タイプのメッセージの数を数えるクエリを作成しようとしています。
例えば次の表がある場合:
--------------------------- id | user_id | message_type --------------------------- 1 | 1 |プライベート 2 | 1 | public 3 | 1 |民間 - - - - - - - - - - - - - -
次に、以下を取得します。
--------------------- id |プライベート| public --------------------- 1 | 2 | 1 ---------------------
したがって、実際にはmessage_typeとuser_idでグループ化したいのですが、ユーザーごとに複数の行を生成するのではなく、message_typeごとに1つずつ、複数の列を作成したいと思います。
クエリでメッセージタイプをハードコーディングせずにこれを実現できますか?
列に変換する値の数が限られている場合は、CASE
式を使用した集計関数を使用して簡単に実装できます。
_select user_id,
sum(case when message_type = 'private' then 1 else 0 end) private,
sum(case when message_type = 'public' then 1 else 0 end) public
from yourtable
group by user_id
_
PostgreSQLには、_ tablefunc モジュールをインストールすることで使用できるcrosstab()
を使用する機能があります。これにより、行から列への同様のデータ変換が実行されます。クエリの動的バージョンを作成することは簡単なプロセスではありません。これが StackOverflowの動的クロス集計 の優れたソリューションです。
PostgreSQLは、PIVOTを直接サポートしていません。PIVOTは、通常、他のプラットフォームでこのような目的で使用されるキーワードです。 (tablefunc モジュールには、doesのクロス集計関数がいくつかあります。
crosstab()関数を使用 、(優れたStackOverflow回答)