mysql:8667
From: ML account <ML account <ml@xxxxxxxxxx>>
Date: Wed, 28 Jan 2004 02:58:30 +0900
Subject: [mysql 08667] Re: 複数フィールドに対する頻度集計
こんにちは。 Kenichi-Ashida <ashiken@xxxxxxxxxx>さんの <200401271528.HID37607.LBJFIOT@xxxxxxxxxx> "[mysql 08662] 複数フィールドに対する頻度集計" > あしだ@MySQL初心者です > ちょっと悩んでいます。 ビューやサブクエリが使えれば、スマートかどうかは別にしても簡単なのです けどね。 CREATE TABLE table1 ( id INT NOT NULL PRIMARY KEY, Field1 varchar(20), Field2 varchar(20), Field3 varchar(20) ); の様なテーブル構造なら、一度テンポラリテーブルに出してから集計する方法が 比較的簡単です。3.23ではUNION操作が使えないと思いますので、ベタな方法で。 CREATE TABLE tmp000 (FldData varchar(20)); INSERT INTO tmp000 (FldData) SELECT Field1 AS FldData FROM table1 INSERT INTO tmp000 (FldData) SELECT Field2 AS FldData FROM table1 INSERT INTO tmp000 (FldData) SELECT Field3 AS FldData FROM table1; SELECT FldData,count(*) AS cnt FROM tmp000 WHERE FldData IS NOT NULL GROUP BY FldData ORDER BY cnt DESC; あるいは、 CREATE TABLE tmp000 (FldData varchar(20),cnt INT); INSERT INTO tmp000 (FldData,cnt) SELECT Field1 AS FldData,count(*) AS cnt FROM table1 GROUP BY FldData INSERT INTO tmp000 (FldData,cnt) SELECT Field2 AS FldData,count(*) AS cnt FROM table1 GROUP BY FldData INSERT INTO tmp000 (FldData,cnt) SELECT Field3 AS FldData,count(*) AS cnt FROM table1 GROUP BY FldData; SELECT FldData,sum(cnt) AS cnt FROM tmp000 WHERE FldData IS NOT NULL GROUP BY FldData ORDER BY cnt DESC; [mysql 08565]でも述べた、テーブルの正規化を考慮する事も一案でしょう。 CREATE TABLE table1 (id INT NOT NULL PRIMARY KEY); CREATE TABLE table1s ( id INT NOT NULL, colpos INT NOT NULL, coldata VARCHAR(20) ); なテーブルがあった場合、 > <Table1> > [ID] [Field1] [Field2] [Field3] の表を得るクエリは、 SELECT table1.id AS ID, T1.coldata AS Field1, T2.coldata AS Field2, T3.coldata AS Field3 FROM ((table1 LEFT JOIN table1s AS T1 ON table1.id = T1.id) LEFT JOIN table1s AS T2 ON table1.id = T2.id) LEFT JOIN table1s AS T3 ON table1.id = T3.id WHERE T1.colpos=1 AND T2.colpos=2 AND T3.colpos=3 ORDER BY table1.id; となり、「希望する集計結果」を得るクエリは、 SELECT table1s.coldata, count(*) AS cnt FROM table1s,table1 WHERE table1s.coldata IS NOT NULL AND table1.id=table1s.id GROUP BY table1s.coldata ORDER BY cnt DESC の様な感じになります。 表を得るクエリと集計を得るクエリで、どちらが使用頻度が多いのか、どちら がクエリ実行の時間的な制約がきついのかで、この正規化した方法が妥当なのか、 それとも最初に述べたベタなテーブルでやる方が妥当なのかは変わって来るでし ょう。 また正規化した方法では、データ挿入/変更時に一貫性を保証する手段(テーブル のロックまたはトランザクション)が必要となる場合もあるでしょう。 松枝知直 <tomom@xxxxxxxxxx> http://www.argus.ne.jp/~tomom/
8662 2004-01-27 15:28 [Kenichi-Ashida <ashi] 複数フィールドに対する頻度集計 -> 8667 2004-01-28 02:58 ┗[ML account <ml@xxxxx] 8668 2004-01-28 11:21 ┗[Kenichi-Ashida <ashi] 8669 2004-01-28 15:29 ┗[ML account <ml@xxxxx]