Допиливал статистику игрового сервера: http://109.86.199.237/stats/ На главной странице я добавил внизу блок "Суперзвёзды сервера", в итоге страница стала заметно дольше грузиться. Каждая строчка этого блока это 1-2 отдельных запросов в БД. Код целиком здесь приводить не буду, ибо многабукаф, но сами запросы вот они: PHP: <?php //Покрыл наибольшее расстояние $query = mysql_query("SELECT uuid, player_name, distance_traveled FROM `players` ORDER BY distance_traveled DESC LIMIT 1"); $row = mysql_fetch_array($query); //Поставил больше всех блоков $query = mysql_query("SELECT uuid FROM `blocks` GROUP BY uuid"); while ($row = mysql_fetch_array($query)) { $players[]=$row['uuid']; } foreach ($players as $uid) { $row = mysql_fetch_assoc(mysql_query("SELECT SUM(num_placed) AS placedTotal FROM blocks WHERE uuid = '$uid'")); $blocks_placed[$uid]=$row['placedTotal']; } //Уничтожил больше всех блоков $query = mysql_query("SELECT uuid FROM `blocks` GROUP BY uuid"); while ($row = mysql_fetch_array($query)) { $players[]=$row['uuid']; } foreach ($players as $uid) { $row = mysql_fetch_assoc(mysql_query("SELECT SUM(num_destroyed) AS destroyedTotal FROM blocks WHERE uuid = '$uid'")); $blocks_destroyed[$uid]=$row['destroyedTotal']; } //Самый опасный убийца мобов $query = mysql_query("SELECT killed_by_uuid FROM `kills` GROUP BY killed_by_uuid"); while ($row = mysql_fetch_array($query)) { if ($row['killed_by_uuid']) { $players[]=$row['killed_by_uuid']; } } foreach ($players as $uid) { $k12 = mysql_fetch_array(mysql_query("SELECT COUNT(*) FROM `kills` WHERE killed_by_uuid ='$uid'")); $kills[$uid] = $k12[0]; } //Умер наибольшее количество раз $query = mysql_query("SELECT killed_uuid FROM `kills` GROUP BY killed_uuid"); while ($row = mysql_fetch_array($query)) { if ($row['killed_uuid']) { $players[]=$row['killed_uuid']; } } foreach ($players as $uid) { $k12 = mysql_fetch_array(mysql_query("SELECT COUNT(*) FROM `kills` WHERE killed_uuid ='$uid'")); $deaths[$uid] = $k12[0]; } //Самый активный игрок $query = mysql_query("SELECT uuid, player_name, num_secs_loggedon FROM `players` ORDER BY num_secs_loggedon DESC"); $row = mysql_fetch_array($query); ?> Так вот, у меня вопрос - влияет ли вообще количество запросов на производительность, или тут всё зависит только от объёма выкаченной из БД информации? И если влияет, то реально ли объединить все эти запросы в 2-3?
в 12, 23, 37 и 51 строках надо не делать запрос в цикле, а в цикле собрать список uids и выбирать из базы одним запросом. Это уже может неплохо помочь
//Поставил больше всех блоков $query = mysql_query("SELECT uuid FROM `blocks` GROUP BY uuid"); while ($row = mysql_fetch_array($query)) { $players[]=$row['uuid']; } foreach ($players as $uid) { $row = mysql_fetch_assoc(mysql_query("SELECT SUM(num_placed) AS placedTotal FROM blocks WHERE uuid = '$uid'")); $blocks_placed[$uid]=$row['placedTotal']; } Тут я бы просто написал 1 запрос: SELECT distinct b.uuid, (SELECT SUM(num_placed) FROM blocks WHERE uuid = b.uuid) as placedTotal FROM `blocks` b ORDER BY placedTotal DESK LIMIT 1 Соответственно и для других блоков так же по запросу. Так как в основном время тратится на установку соединения к БД и лучше записать один большой запрос чем десятки маленьких. Потом увидел 2 одинаковых запроса "SELECT uuid FROM `blocks` GROUP BY uuid" Нафига? Если один раз уже был. Можно использовать уже сконструированную переменную. Либо что бы вообще не заморачиваться пишем все в одном запросе: SELECT b.uuid, (SELECT count(*) FROM `blocks` where uuid=b.uuid) as count, (SELECT SUM(num_placed) FROM `blocks` where uuid=b.uuid) as placedTotal FROM `blocks` b GROUP by uuid ORDER BY count DESC, placedTotal DESC LIMIT 2 Здесь первая позиция будет максимальное количество, вторая позиция максимальная сумма. только нужно будет сравнить максимальную сумму 2 позиции с 1 позицией. Возможно что 1 будет больше.
Короче, сделал так. Работать стало заметно быстрее, я прямо таки горжусь собой. 8)) Но нет предела совершенству. Можно ли сделать ещё меньше запросов? PHP: <?php //Покрыл наибольшее расстояние $query = mysql_query("SELECT uuid, player_name, distance_traveled FROM `players` ORDER BY distance_traveled DESC LIMIT 1"); $row = mysql_fetch_array($query); $distance[0]=$row['uuid']; $distance[1]=$row['player_name']; $distance[2]=QueryUtils::formatDistance($row['distance_traveled']); //Поставил больше всех блоков $row = mysql_fetch_assoc(mysql_query("SELECT SUM(num_placed) AS placedTotal, uuid FROM `blocks` GROUP BY uuid ORDER BY placedTotal DESC LIMIT 1")); $_player = $serverObj->getPlayer($row['uuid']); $placed[0]=$row['uuid']; $placed[1]=$_player->getName(); $placed[2]=$row['placedTotal']; unset($blocks); //Уничтожил больше всех блоков $row = mysql_fetch_assoc(mysql_query("SELECT SUM(num_destroyed) AS destroyedTotal, uuid FROM `blocks` GROUP BY uuid ORDER BY destroyedTotal DESC LIMIT 1")); $_player = $serverObj->getPlayer($row['uuid']); $destroyed[0]=$row['uuid']; $destroyed[1]=$_player->getName(); $destroyed[2]=$row['destroyedTotal']; //Самый опасный убийца мобов $query = mysql_query("SELECT COUNT(killed_by_uuid) AS killsTotal, killed_by_uuid FROM `kills` GROUP BY killed_by_uuid ORDER BY killsTotal DESC LIMIT 2"); $row = mysql_fetch_array($query); if (!$row['killed_by_uuid']) { $row = mysql_fetch_array($query); } //предохранитель на случай, если пустых записей больше всего $_player = $serverObj->getPlayer($row['killed_by_uuid']); $killer[0]=$row['killed_by_uuid']; $killer[1]=$_player->getName(); $killer[2]=$row['killsTotal']; //Умер наибольшее количество раз $query = mysql_query("SELECT COUNT(killed_uuid) AS killedTotal, killed_uuid FROM `kills` GROUP BY killed_uuid ORDER BY killedTotal DESC LIMIT 2"); $row = mysql_fetch_array($query); if (!$row['killed_uuid']) { $row = mysql_fetch_array($query); } //предохранитель на случай, если пустых записей больше всего $_player = $serverObj->getPlayer($row['killed_uuid']); $killed[0]=$row['killed_uuid']; $killed[1]=$_player->getName(); $killed[2]=$row['killedTotal']; //Самый активный игрок $query = mysql_query("SELECT uuid, player_name, num_secs_loggedon FROM `players` ORDER BY num_secs_loggedon DESC"); $row = mysql_fetch_array($query); $active[0]=$row['uuid']; $active[1]=$row['player_name']; $active[2]=QueryUtils::formatSecs($row['num_secs_loggedon']); ?>