質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
MySQL

MySQL(マイエスキューエル)は、TCX DataKonsultAB社などが開発するRDBMS(リレーショナルデータベースの管理システム)です。世界で最も人気の高いシステムで、オープンソースで開発されています。MySQLデータベースサーバは、高速性と信頼性があり、Linux、UNIX、Windowsなどの複数のプラットフォームで動作することができます。

Q&A

解決済

2回答

3914閲覧

【MySQL】累積度数のグラフ作成のために、毎月の累積数を一度に取得したい。

Satochan24

総合スコア113

MySQL

MySQL(マイエスキューエル)は、TCX DataKonsultAB社などが開発するRDBMS(リレーショナルデータベースの管理システム)です。世界で最も人気の高いシステムで、オープンソースで開発されています。MySQLデータベースサーバは、高速性と信頼性があり、Linux、UNIX、Windowsなどの複数のプラットフォームで動作することができます。

0グッド

0クリップ

投稿2016/02/22 05:19

編集2016/02/24 04:58

【2016/2/24追記その2】
以前、ここで新規ユーザ数を出してもらったSQLが下記のようにあり、このSQLと、先程の追記のSQLを
結合できれば、できそうですが...苦戦しています。

【毎月の新規ユーザのみ】

SELECT ( a.access_month ) AS access, b.newer_count AS newer FROM ( SELECT access_month, count( * ) AS all_count FROM ( SELECT DISTINCT user_id, date_format( access_day, '%Y年%m月' ) AS access_month FROM access_record WHERE access_type =101 ) AS c GROUP BY access_month)a LEFT JOIN ( SELECT access_month, count( * ) AS newer_count FROM ( SELECT user_id, min( date_format( access_day, '%Y年%m月' ) ) access_month FROM access_record GROUP BY user_id ) AS d GROUP BY access_month)b ON a.access_month = b.access_month ORDER BY `a`.`access_month` DESC LIMIT 12

【2016/2/24追記】
現在、下記のSQLまで作成し、最新月を先頭にし、1年間表示に絞り、完成に近い状態なのですが、
できれば、累積の新規ユーザ数の隣に、その月の新規ユーザ数も表示させたいと思います。
別の表を結合するしかないかなぁと考えていますが…
何か方法ありますでしょうか?

【累積の新規ユーザ数】

SELECT date_format( M.last_date, '%Y年%m月' ) AS mon, count( * ) AS cnt FROM ( SELECT DISTINCT last_day( access_day ) AS last_date FROM access_record ) AS M JOIN ( SELECT user_id, min( access_day ) AS user_date FROM access_record GROUP BY user_id ) AS U WHERE M.last_date >= U.user_date GROUP BY M.last_date ORDER BY mon DESC LIMIT 12

【以下、元々の質問】
アプリの新規の使用ユーザーを累積度数でグラフ化したいと
思いまして、その値を取得するSQLを考えています。
以下の通り、部分的には取得できています。

【全新規ユーザ数】

SELECT COUNT( * ) FROM ( SELECT user_id, min( date_format( access_day, '%Y-%m' ) ) access_month, access_day FROM access_record GROUP BY user_id ) AS a

また、今月の増加した新規ユーザ数は、

SELECT COUNT( * ) FROM ( SELECT user_id, min( date_format( access_day, '%Y-%m' ) ) access_month, access_day FROM access_record GROUP BY user_id ) AS a WHERE date_format( access_day, '%Y-%m' ) >= date_format( DATE_SUB( NOW( ) , INTERVAL 1 MONTH ) , '%Y-%m' ) AND date_format( access_day, '%Y-%m' ) < date_format( NOW( ) , '%Y-%m' )

先月に増加した新規ユーザ数は

SELECT COUNT( * ) FROM ( SELECT user_id, min( date_format( access_day, '%Y-%m' ) ) access_month, access_day FROM access_record GROUP BY user_id ) AS a WHERE date_format( access_day, '%Y-%m' ) >= date_format( DATE_SUB( NOW( ) , INTERVAL 2 MONTH ) , '%Y-%m' ) AND date_format( access_day, '%Y-%m' ) < date_format( DATE_SUB( NOW( ) , INTERVAL 1 MONTH ) , '%Y-%m' )

で得られました。あとは、変数に入れて引き算してやれば
累積度数の値は得られると思うのですが、
1年分作成使用とした場合、SQLが多くなってしまいます。

何か、1つのSQLで1年分取得する方法はありますでしょうか?
最新月のグラフの値は、常に、アクセスのカウント取得開始してからの累積値にしたいと思っています。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答2

0

ベストアンサー

下記でそれっぽいものが出るかもしれません。

sql

1select date_format(M.last_date, '%Y/%m') as mon, count(*) as cnt from ( 2 select distinct last_day(access_day) as last_date from access_record 3) as M 4 join ( 5 select user_id, min(access_day) as user_date from access_record group by user_id 6) as U 7where M.last_date >= U.user_date 8group by M.last_date;

↑のSQLまで至った経緯。

sql

1/* 月末の一覧 */ 2select distinct last_day(access_day) as last_date from access_record; 3 4/* ユーザーごとの最初のアクセス日 */ 5select user_id, min(access_day) as user_date from access_record group by user_id; 6 7/* ↑2つの積集合 */ 8select * from ( 9 select distinct last_day(access_day) as last_date from access_record 10) as M 11 join ( 12 select user_id, min(access_day) as user_date from access_record group by user_id 13) as U 14order by M.last_date, U.user_date; 15 16/* ↑の集合から「ユーザーのアクセス日」が「各月末の日付」よりも小さいものを除外 */ 17select * from ( 18 select distinct last_day(access_day) as last_date from access_record 19) as M 20 join ( 21 select user_id, min(access_day) as user_date from access_record group by user_id 22) as U 23where M.last_date >= U.user_date 24order by M.last_date, U.user_date; 25 26/* ↑の結果を月末の日付でグループ化 */ 27select date_format(M.last_date, '%Y/%m') as mon, count(*) as cnt from ( 28 select distinct last_day(access_day) as last_date from access_record 29) as M 30 join ( 31 select user_id, min(access_day) as user_date from access_record group by user_id 32) as U 33where M.last_date >= U.user_date 34group by M.last_date;

累積の新規ユーザ数の左隣りに、その月の新規ユーザ数も表示させたいのですが

sql

1select 2 date_format(M.last_date, '%Y/%m') as mon, 3 count(*) as tcnt, 4 sum(last_day(M.last_date) = last_day(U.user_date)) as mcnt 5from ( 6 select distinct last_day(access_day) as last_date from access_record 7) as M 8 join ( 9 select user_id, min(access_day) as user_date from access_record group by user_id 10) as U 11where M.last_date >= U.user_date 12group by M.last_date;

投稿2016/02/22 10:12

編集2016/02/24 04:42
ngyuki

総合スコア4514

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Satochan24

2016/02/24 02:41

回答有難うございました。 なぜ、最初の短いSQLで取得できるのか、まだあまり理解できていませんが、 欲しかった情報は得られていました。 最終的にどうするか。PHPの出力部分完了したら、解決処理します。
Satochan24

2016/02/24 04:37

度々、すみません。質問にも追記したのですが、 累積の新規ユーザ数の左隣りに、その月の新規ユーザ数も表示させたいのですが、 何か方法等ありますでしょうか?別の表を結合させる必要があるかなぁと思っていますが…
ngyuki

2016/02/24 04:42

回答に追記しました
Satochan24

2016/02/24 05:02

早速の回答有難うございます。 すごい!こんな短いSQLで表示できるとは思いませんでした。 有難うございました。
guest

0

SQLの負荷は考慮していません。

SQL

1SELECT 2 YM, 3 (SELECT COUNT(DISTINCT S.user_id) 4 FROM access_record S 5 WHERE S.access_day < date_format(A.access_day, '%Y-%m-1')) + COUNT(*) AS CNT 6FROM ( 7SELECT 8 user_id, 9 date_format(MIN(access_day), '%Y-%m' ) AS YM, 10 access_day 11FROM access_record 12GROUP BY user_id) A 13GROUP BY YM 14ORDER BY YM DESC 15LIMIT 12

意図している結果になるかご確認ください。

投稿2016/02/22 10:05

dupont_kedama

総合スコア925

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Satochan24

2016/02/24 02:50

回答有難うございました。 欲しい結果が得られていました。 ただ、新規ユーザーがいない月は、その月が表示されなかったので、 表示されたほうがいいかなぁと思いました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問