Как узнать количество записей в SQL-выборке
Очень часто нам не требуется извлекать данные из таблицы, однако, нам необходимо узнать количество записей в определённой SQL-выборке, в частном случае, количество записей в таблице. Вот как узнать количество записей в SQL-выборке, я расскажу в этой небольшой статье.
На самом деле всё очень просто, и нам нужна всего лишь функция COUNT():
SELECT COUNT(*) FROM `table` WHERE `field_1`='value_1'
После выполнения данного запроса будет возвращён result_set, в котором будет храниться массив, содержащий элемент COUNT(*) со значением количества записей в таблице "table", где поле "field_1" имеет значение "value_1".
Другой пример. Допустим, надо узнать просто количество записей. Тогда то же самое, но без WHERE:
SELECT COUNT(*) FROM `table`
И давайте, напоследок, подкину ещё один пример. Допустим, Вам необходимо подсчитать количество уникальных записей в таблице:
SELECT COUNT(DISTINCT `field_1`) FROM `table`
Вот такой нехитрой функцией COUNT() можно легко узнавать количество записей в SQL-выборке, не извлекая при этом сами записи и экономя ресурсы.
Полный курс по PHP и MySQL: http://srs.myrusakov.ru/php
-
- Михаил Русаков
Комментарии (45):
Михаил, здравствуйте! Хотел бы попросить у Вас помощи. Почему на реальном хостинге этот запрос не работает $res_articles = $mysqli->query("SELECT id,title,cp_title,description,images,author,DATE_FORMAT(date,'%d %M %Y') as date FROM articles WHERE tg='0' ORDER BY id DESC LIMIT $shift,$num_data"); Проблема в - LIMIT $shift,$num_data - не пойму почему не работает с переменными! Перепробовал все варианты, уже два дня голову ломаю :((( Если Вас не затруднит можете дать совет.
Ответить
Вряд ли дело в хостинге, Вы проверьте значения переменных shift и num_data. А также "не работает" понятие растяжимое. Выдаются ли какие-нибудь ошибки? Или просто пустой результат выходит?
Ответить
Пустой результат, но когда убираю LIMIT $shift,$num_data или пишу вместо переменных LIMIT 2, 5 то всё ОК. А может переменные привести к числу через integer?
Ответить
Тогда проблема в значении переменных, можете ещё попробовать через соединение строк: "LIMIT ".$shift.", ".$num_data
Ответить
Я так пробовал всё равно пустой результат, но в переменных лежат числа я проверял конечно я не проверял на int
Ответить
Посмотрите, что в этой строке (всё ли правильно): echo "SELECT id,title,cp_title,description,images,author,DATE_FORMAT(date,'%d %M %Y') as date FROM articles WHERE tg='0' ORDER BY id DESC LIMIT $shift,$num_data";
Ответить
Сейчас проверяю, главное что на localhoste всё работает
Ответить
Вывод после echo - SELECT id,title,cp_title,description,author,images,DATE_FORMAT(date,'%d %M %Y') as date FROM articles WHERE tg='0' ORDER BY id DESC LIMIT -10,10.
Ответить
Видите, что запрос неправильный? Вот и подумайте, почему -10 подставляется.
Ответить
Спасибо Михаил за помощь разобрался просто в функции не изменил один параметр
Ответить
Михаил, подскажи, пожалуйста, а как переделать этот запрос: SELECT COUNT(*) FROM `table` WHERE `field_1`='value_1' для нескольких значений 'value' ??? так чтоб одним запросом считать количество записей для нескольких значений поля field_1. Или по-любому надо несколько аналогичных запросов делать?
Ответить
http://myrusakov.ru/sql-union.html
Ответить
SELECT COUNT(*) FROM `table` WHERE `field_1`='value_1' UNION SELECT COUNT(*) FROM `table` WHERE `field_1`='value_2' UNION SELECT COUNT(*) FROM `table` WHERE `field_1`='value_3' ... и т.д.??? А если таких запросов 20 или еще больше, то такой запрос будет нормальным?
Ответить
Вполне, он будет работать гораздо быстрее, чем 20 простых.
Ответить
Спасибо большое!!!
Ответить
что-то оно считает только первый SELECT. Или я что-то делаю неправильно. :) $result_set = $mysqli->query("тут тройной запрос, который я выше указывал"); потом $row = $result_set->fetch_assoc(); $result_set->close(); print_r($row); и выдает только первый COUNT: Array ( [COUNT(*)] => 52 ). Получается, что срабатывает только первый COUNT и все. Подскажи, пожалуйста, что не так делаю?
Ответить
Нужно по-другому называть COUNT(*), например, так COUNT(*) as `r_1`, потом COUNT(*) as `r_2` и так далее.
Ответить
Array ( [r_1] => 52 ) теперь так начало выдавать :). все равно только первый SELECT срабатывает и останавливается. UNION не срабатывает. или опять что-то не так.
Ответить
Покажите изменённый запрос, кусок какой-нибудь из 3 UNION.
Ответить
1. SELECT COUNT(*) FROM `table` WHERE `field_1` in ('value_1','value_2',...,'value_20') 2. Лучше запросов с явными значениями в них избегать. Запросы нужно строить с параметрами: SELECT COUNT(*) FROM `table` WHERE `field_1`=? 3. В данном случае не очевидно, как построить запрос с параметром, чтобы он выбрал необходимые 20 строк. Но ведь как-то автор для себя решил, как эти 20 строк должны быть выбраны? Например, они относятся к какой-то группе данных, идентификатор которой записан в field2. Тогда SELECT COUNT(*) FROM `table` WHERE `field_2`=? 4. После UNION [ALL] в следующем SELECT field1 as ALIAS2 - алиас ставить бессмысленно. alias выберется еще из самого 1-го SELECT, а все остальные просто проигнорируются.
Ответить
$result_set = $mysqli->query("SELECT COUNT(*) as `r_1` FROM `works` WHERE `razdelName`='sol_testo' AND `del`='' UNION SELECT COUNT(*) as `r_2` FROM `works` WHERE `razdelName`='tochka_k_tochke' AND `del`='' UNION SELECT COUNT(*) as `r_3` FROM `works` WHERE `razdelName`='svad_decor' AND `del`=''");
Ответить
неправильно пишет del. `del`='пробел'. вернее ничего просто нету вместо пробела, просто две ', а отображает как кавычку. :)
Ответить
Сделайте вместо UNION - UNION ALL. Тогда получится только 1 r_1, но зато это будет массив из нескольких значений.
Ответить
ок, спасибо большое!
Ответить
а куда вставлять UNION ALL??? один раз и в какое место? или перед каждым SELECT?? что-то ничего не меняется.
Ответить
Перед каждым.
Ответить
Добавил перед каждым UNION ALL SELECT COUNT(*) as `r_1` FROM `works` WHERE `razdelName`='sol_testo' AND `del`='' UNION ALL SELECT COUNT(*) as `r_2` FROM `works` WHERE `razdelName`='tochka_k_tochke' AND `del`='' UNION ALL SELECT COUNT(*) as `r_3` FROM `works` WHERE `razdelName`='svad_decor' AND `del`='' Выдает ошибку Fatal error: Call to a member function fetch_assoc() on a non-object. Сделал так, чтоб все запросы делались отдельно - так работает. Так наверно и оставлю. :) Все равно СПАСИБО за попытку помочь! :)
Ответить
Ещё раз повторяю: замените UNION на UNION ALL. У Вас разве был перед первым select UNION? Нет? Тогда зачем добавляли?
Ответить
убрал перед первым SELECTом и стало как и раньше выдавать только один Array ( [r_1] => 52 ) и все. Ладно, Михаил, для меня это не критично сейчас. Отдельно все считает как мне надо и слава Богу! :)) Спасибо еще раз.
Ответить
Не может такого быть, значит, опять что-то сделали не так. Я проверил лично данный запрос у себя, и у меня всё прекрасно работает. Внимательнее надо делать то, что я пишу.
Ответить
Здравствуйте Михаил. Пожскажите пожалуйста, я сделал запрос на количество записей, но как вывести результат? он пустой. Зараннее спасибо
Ответить
Для начала нужно написать такой запрос, чтобы он не был пустым, а уже потом что-то выводить.
Ответить
<?php connectDB(); $result_set = $mysqli->query("SELECT COUNT(*) FROM `articles`"); while ($row = $result_set->fetch_assoc()){ ?> <p>Статей на сайте: <b><?php echo $row[0];?></b></p> <?php } $result_set->close(); closeDB(); ?> вот я сделал запрос, но он не работает, пусто, не подскажете, в чем я ошибся
Ответить
$row["COUNT(*)"] - вот так нужно выводить.
Ответить
спасибо за помощь, но я в свою очередь попробовал сделать так: <?php connectDB(); $result_set = $mysqli->query("SELECT COUNT(*) FROM `articles`"); $mysqli_fetch_arrey($result_set) ?> <p>Статей на сайте: <b><?php echo $row[0];?></b></p> <?php $result_set->close(); closeDB(); ?> есть ли между ними принципиальная разница? ведь результат получается один.
Ответить
Не стоит смешивать ООП и процедурный стиль.
Ответить
если я правильно понял, ваше решение - это ООП, а мое - это процедурный стиль?
Ответить
У Вас всё перемешано, сначала ->query (ООП), а потом mysqli_fetch_arrey (процедурный стиль).
Ответить
Вопрос может быть не в тему, но вот: Есть sql файл с данными для вставки в таблицу. Перед вставкой записи, нужно проверить существует ли такая запись в таблице. интуитивно понимаю что это дело проверяется триггером before insert, а вот как его написать так и не разобрался. Помогите пожалуйста.
Ответить
Юрий, запросто. Проверяем для начала таблицу на наличие данной записи, и если ее нет, то вставляем. Пример: $query = "select * from `users` where `name` = 'Юрий'"; $result = mysql_query($query,$db); if(!mysql_fetch_array($result)){// если нет записи с полем Юрий, то..
Ответить
Это средствами php, мне же нужно без всякого php а просто триггером.
Ответить
Здравствуйте Михаил. Не скажите а есть какой то другой способ для расчета количество записей в выборке? Потому что у меня запрос COUNT(*) займет 30-40 сек. В базе примерно 6 миллион записей.
Ответить
SELECT DISTINCT `column1` FROM `my_table`; SELECT FOUND_ROWS(); Если вбить в phpmyadmin, действительно возвращает количество уникальных записей, но в PHP достучаться до этого числа мне не удалось, не вывелся даже Resourse.
Ответить
Если в базе (правильнее в таблице) 6 млн. записей, то уже точно имеет смысл задуматься об оптимизации запроса. Быстрее COUNT(*) может отработать только COUNT(*) :))) Вот прям нужно посчитать ВСЕ записи в таблице? Скорее всего есть какое-то условие в WHERE? Вот тогда можно проиндексировать таблицу, чтобы счет шел не по FULL SCAN, а по индексу.
Ответить
Здравствуйте, Михаил. Подскажите, сколько всего(максимум) записей sql запрос может вытащить(через Select)?
Ответить
Для добавления комментариев надо войти в систему.
Если Вы ещё не зарегистрированы на сайте, то сначала зарегистрируйтесь.