SQLで何でもやる派と、
DBは、できるだけ簡単に取ってきて、プログラムでがんばる派
と2通りがある。どちらも主義主張がある。
といっても、良くわからないと思うので、実例で説明する。
■進捗の例:御題
以下のテーブルがある
つまり、shinchokuというテーブルがあり、カラムはid,group_id,doneよりなる。
このうち、doneが1のものは手続き済み、0のものは手続きしていないとしたとき、
各グループで、手続き完了している人の割合(doneが1の人/グループ全体の人)
を求めたい。
という御題。ま、同じようなことで進捗率なども見れる。
■SQLで何でもやる
基本的に、このようなものは、数を求めたいのでcountを使う。
countは列名を指定した場合、NULLは数えない。そこで
shinchokuテーブルをAという名前にして、Aテーブルには全部を出す
shinchokuテーブルをBという名前にして、Bテーブルには手続き完了の人を出す。
これを、Aテーブルに対してLEFT JOIN Bテーブル
(a.id=bidとする)すると・・・
上記の例だと、こんなかんじになる。
Bテーブルには、手続きが終わっていない人(done=0)は含まれないので、
AテーブルとLEFT JOINすると、そのような人のBテーブルの
内容はNULLになる。
そこで、
AテーブルのIDを数えると(count)すると、全部
BテーブルのIDを数えると(count)すると、手続き完了の人
となる。あとは、グループごとに集計すればいい
結果として、以下のSQL
SELECT A.group_id,count(B.id).conut(A.id)
FROM shinchoku AS A
LEFT JOIN shinchoku AS B ON A.id=B.id AND B.done=1
GROUP BY A.group_id
となる。実行するとこんなかんじ
■プログラムでがんばる
SQLで全データをとってきて、総数と手続き完了の人の配列を求め
レコードごとに、
総数の配列の該当グループに1を足す
完了のレコードが出てきたら
完了の配列の該当グループに1を足す
そうすると、各グループごとに総数と手続き完了の人の数が、配列に入ってくる
んで、それを表示
PHPだと、こんなかんじ。なお、ユーザー名はroot,パスワードはなく
データベース名はtestである。
<?php
$host = "localhost";
$user = "root";
$database = "test";
//==============================//
// データベース接続 //
//==============================//
$con = mysql_connect($host, $user)
or die("データベースとの接続に失敗しました");
mysql_select_db($database)
or die("データベースの選択に失敗しました");
mysql_query("SET NAMES utf8");
//==============================//
// データ読み込み //
//==============================//
$query = "select * from shinchoku";
$result = mysql_query($query);
mysql_close($con);
//==============================//
// 集計 //
//==============================//
$sosu = array();
$done = array();
while ($row = mysql_fetch_assoc($result))
{
// グループが始めて出てきたとき
$group_id = $row['group_id'];
if ( isset($sosu[$group_id]) == false )
{
$sosu[$group_id] = 0;
$done[$group_id] = 0;
}
// 全体数の集計
$sosu[$group_id]++;
// 終わった人の集計
if ($row['done'] == 1 )
{
$done[$group_id]++;
}
}
//==============================//
// 表示 //
//==============================//
foreach ($sosu as $key => $value)
{
print($key . ":" . $done[$key] . "," . $value ."<BR/>");
}
?>
|
■違いは・・・
いろんな主義主張はあるだろう。
ここでは議論しない。
しかし、向き不向きがあって、
はじめのSQLでがんばる派は、JOINが遅いと、厳しくなってくる。
5個か6個のテーブルをJOINすると、結構大変になってくるんじゃないかな・・
後者は、その点SQLは、単純なんだけど、プログラムが長くなり、
大変そうに「見える」(実は中身は簡単なんだけど)