- ベストアンサー
select文でGROUP BYの正しい使い方
下記のselect文は問題ないでしょうか?テーブルには5つのフィールド(id,name,age,gender,office)が存在します。 select * from テーブル名 where age >= '40' GROUP BY gender 実際に試したところ、うまく動いているのですが、GROUP BY句で指定されたフィールド名はSELECT句のフィールド指定をすべて含んでいなくてはならないと書かれているのを見つけました。 上記のselect文は正しいのでしょうか。
- みんなの回答 (3)
- 専門家の回答
質問者が選んだベストアンサー
ん・・・動かないSQL文のように見えるのですが・・・ select句の後に指定された列はグループ関数が使われているか group by句によるグループ化の基準として使われていなければなりません。 group by句によってグループ化された場合グループにつき1行の結果が返ってきます。 グループには複数の行が含まれる可能性があります。 その結果グループ数とデータ行数の不一致が起こり出力する事ができない状態になるため グループ化の基準として使われない列1グループにつき1行を返すグループ化関数を適用しなければなりません。 select * from テーブル名 where age >= '40' GROUP BY gender の場合genderはおそらく3行(nullがありえるため)か2行になると思いますがその他の列は40歳以上の人の人数分の行が出てくることになります。 それは出力のしようがありません。 ですのでこのSQL文は動くとは思えません。 ただ・・・DBMSが何かを補完する可能性がないわけではないですが・・・
その他の回答 (2)
- みずの(@mizuno3)
- ベストアンサー率73% (192/263)
GROUP BY句で指定されているのがgenderということで、やりたいことは「男性、女性、それぞれの人数を出したい。」とかのSQLじゃないのでしょうか? その場合、 SELECT count(*) as num, gender テーブル名 where age >= '40' GROUP BY gender; とかになるんじゃないでしょうか? 男女それぞれの年代までを知りたいのであればGROUP BY句にageが追加されるとかってことになると思います。 SELECT gender, age, count(*) as num テーブル名 where age >= '40' GROUP BY gender, age; 行いたい動作を書くことで、それが正しいかどうかも解かるのではないでしょうか。 izayoimizukiさんとseta_takahiroさんの書かれているように、動くかも知れないけどおかしいと思います。
お礼
たまたまうまくいってるように見えるだけのようなので、他のやり方で試してみることにします。どうもありがとうございました。
- seta_takahiro
- ベストアンサー率60% (23/38)
普通は間違っていると思うのですが、データベースソフトによっては許可されていると思います。 たとえば、MySQLなら http://dev.mysql.com/doc/refman/5.1/ja/group-by-hidden-fields.html にあるように、そういう文法を許すと思います。 (おそらく、上の使いかただと出力は不定だと思いますが) たしか、Oracleでも使えたような気がします。 (自分は動作が良く分からなくなるので使いません)
お礼
たまたまうまくいってるように見えるだけのようなので、他のやり方で試してみることにします。どうもありがとうございました。
お礼
やはりそうですか・・・ んー どうしてだろう・・・