Постраничная разбивка из mysql

Статус
В этой теме нельзя размещать новые ответы.

irk

Постоялец
Регистрация
18 Май 2009
Сообщения
91
Реакции
2
Есть некоторый код:

PHP:
<?
/* Скрипт выводит всех клиентов фирмы */
$hostname = "хост";
$username = "юзер";
$password = "пасс";
$dbName = "БД";

/* Таблица MySQL, в которой хранятся данные */
$userstable = "clients";

/* создать соединение */
MYSQL_CONNECT($hostname,$username,$password) OR DIE("Не могу создать соединение ");

@mysql_select_db("$dbName") or die("Не могу выбрать базу данных "); 

/* Выбрать всех клиентов */
$query = "SELECT * FROM $userstable";

$result = MYSQL_QUERY($query);

/* Сколько их всего */
$number = MYSQL_NUMROWS($result);

/* Напечатать всех в красивом виде*/

$i = 0;

IF ($number == 0) {
PRINT "<P>Записи в базе данных отсутствуют либо БД на профилактике! Свяжитесь с техподдержкой!";
} ELSEIF ($number > 0) {
PRINT "<P>Общее число клиентов в базе данных: <b>$number</b><BR><BR>";
WHILE ($i < $number){
$name = mysql_result($result,$i,"name");
$adres = mysql_result($result,$i,"adres");
$adres_fakt = mysql_result($result,$i,"adres_fakt");
$tel_mob = mysql_result($result,$i,"tel_mob");
$tel_work = mysql_result($result,$i,"tel_work");
$tel_home = mysql_result($result,$i,"tel_home");
$email = mysql_result($result,$i,"email");
$filials = mysql_result($result,$i,"filials");

PRINT "Клиент <b>$name</b> зарегистрирован в филиале г. <b>$filials</b><BR>";
PRINT "Адрес по прописке <b>$adres</b><BR>";
PRINT "Адрес проживания <b>$adres_fakt</b><BR>";
PRINT "<i>Контактные телефоны:</i></BR>";
PRINT "Мобильный <b>$tel_mob</b><BR>";
PRINT "Рабочий <b>$tel_work</b><BR>";
PRINT "Домашний <b>$tel_home</b><BR>";
PRINT "Email адрес: <b>$email</b><BR>";
PRINT "<BR><BR>";
$i++;
}
PRINT "";
}
?>

как можно разбить вывод этой информации на страницы по 10 на каждой, помогите на примере моего кода, не могу разобраться уже не первый день :(
 
1) изменить SQL запрос
PHP:
SELECT * FROM $userstable LIMIT $x, 10
$x - это будет номер страницы, [который будешь передавать через $_GET массив в ссылке] умноженный на количество выводимых страниц, т.е. 10
2) в самом низу, где
PHP:
$i++; 
} 
PRINT ""; // походу сюда добавить вывод номеров страниц  <-1|2|3->
} 
?>
вот здесь можно подробней посмотреть по поводу изменения SQL запроса

а здесь по поводу всей организации постраничного вывода, и в частности полной реализации на php
 
  • Нравится
Реакции: irk
Посмотрел примеры, огромное спасибо! Весьма поучительно. Номера страниц даже отображаются, но скрипт не работает, видимо что то путаю в переменных))) Знаний у меня пока что не хватает чтобы его прикрутить полноценно...

Вот самый удачный код, говорят рабочий. Но я не могу применить его к своему коду чтобы в конечном счете выводилось все как было раньше + еще и навигация по страницам, слишком много переменных и не могу разобраться что за что отвечает. Может кто поможет переделать мой прежний код :(((((((((

PHP:
/* Соединяемся с базой. Естественно, данные подставляете свои */
$db = mysql_connect(ХОСТ, ЮЗЕР, ПАРОЛЬ);
mysql_select_db(БАЗА, $db);
/* Определяем количество сообщений на странице */
$lim = "2";
@$page = $_GET['page'];
/* Меняем table на название вашей таблицы и не забываем указывать дополнительные параметры выборки (если они у вас есть) */
$res = mysql_query("SELECT COUNT(*) FROM ТАБЛИЦА");
$row = mysql_fetch_array($res);
$posts = $row[0];
$str = ceil($posts/$lim);
if(empty($page) or $page < 0) $page = 1;
if($page > $str) $page = $str;
$start = $page * $lim - $lim;
/* Дальше подставляете свой код вывода данных из базы в цикле, но обязательно укажите LIMIT $start, $lim */
$result = mysql_query("SELECT * FROM ТАБЛИЦА LIMIT $start, $lim",$db);
$myrow = mysql_fetch_array($result); 
do
{printf ("<p>%s</p>",$myrow["tab"]);}
while ($myrow = mysql_fetch_array ($result)); 
/* Дальше все остается без изменений */
echo '<a href=?page='. ($page - 1) .'>Назад</a>  ';
$i=1;
while ($i <= $str)
{
if ($i==$page)
{echo '<strong><a href=?page='.$i.'>'.$i.'</a></strong> ';}
else
{echo '<a href=?page='.$i.'>'.$i.'</a> ';}
$i = $i+1;
}
echo '  <a href=?page='. ($page + 1) .'>Вперед</a>';
 
пользуйся комментариями - никогда не бывает лишним.
и разбивай пустыми строками код на какие-то логические куски
PHP:
<?
$db = mysql_connect(ХОСТ, ЮЗЕР, ПАРОЛЬ);
mysql_select_db(БАЗА, $db);
// количество новостей на страницу
$lim = "2";
// получаем текущий номер страницы
@$page = (int)$_GET['page'];
// считаем общее количество новостей в таблице
$res = mysql_query("SELECT COUNT(*) FROM ТАБЛИЦА");
$row = mysql_fetch_array($res);
$posts = $row[0];
// делим общее количество новостей на количество на странице
// в итоге имеем количество страниц
$str = ceil($posts/$lim);
// если не указана страница или указана неверно, то будем считать, что первая
if(empty($page) or $page < 0) $page = 1;
if($page > $str) $page = $str;
// узнаем с какого номера надо доставать из базы новости
$start = $page * $lim - $lim;
// собственно, достаем $lim новостей, начиная не с первой, а со $start-овой
$result = mysql_query("SELECT * FROM ТАБЛИЦА LIMIT $start, $lim",$db);
// пока можем - выводим текст статьи
$myrow = mysql_fetch_array($result);
do {
    printf ("<p>%s</p>",$myrow["tab"]);
}
while ($myrow = mysql_fetch_array ($result));
// делаем ссылки на предыдущую страницу
echo '<a href=?page='. ($page - 1) .'>Назад</a>  ';
$i=1;
// пока номер ссылки не будет равным общему количеству страниц - выводим ссылки
while ($i <= $str) {
    // если номер равен текущей, то выводим не ссылку, а просто текст
    if ($i==$page) {
        echo '<strong><a href=?page='.$i.'>'.$i.'</a></strong> ';
    }
    // если номер не равен текущей - рисуем обычную ссылку
    else {
        echo '<a href=?page='.$i.'>'.$i.'</a> ';
    }
    // увеличиваем счетчик
    $i = $i+1;
}
//ссылка на следующую страницу
echo '  <a href=?page='. ($page + 1) .'>Вперед</a>';
?>
 
  • Нравится
Реакции: irk
Можно воспользоваться готовым классом, например этим:
 
  • Нравится
Реакции: irk
Постраничный вывод реализуется очень просто в 2 запроса
1) SELECT SQL_CALC_FOUND_ROWS поля FROM таблица .... LIMIT a, b;
2) select FOUND_ROWS();
В первом запросе волшебное слово SQL_CALC_FOUND_ROWS попросит посчитать все значения удовлетворяющие уловиям поиска, но выведет только те, которые определены limit.
Во втором запросе узнаешь сколько сервер насчитал. Отсюда вычисляешь количество страниц :
$pages = ceil($totalrecords/b+); (функция округления до последующего целого).
 
тут человек помимо мускульной стороны интересовался еще и php-шной стороной этого процесса. а select FOUND_ROWS() теоретически может внести неясности и ошибки, так как во-первых может быть в последствии использован с неверными group by или limit'ами и вернет не общее количество строк, а то, которое попадает под условие, а во вторых FOUND_ROWS() работает ничуть не быстрее select count(col_name) по индексированному столбцу - проверял неоднократно.
 
Топик стартер, как вариант делать такой запрос :
PHP:
$userstable = "clients";
$users_perpage = 10;
$gamers_count = mysql_result(mysql_query("SELECT count(*) FROM `{$userstable}`"), 0);
$pages_count = ceil($gamers_count/$users_perpage);
В данном случае $gamers_count общее количество записей в базе, а $users_perpage количество предметов на одной странице
Так же можно ещё более оптимизировать
PHP:
$userstable = "clients";
$users_perpage = 10;
$pages_count = mysql_result(mysql_query("SELECT ceil(count(*)/{$users_perpage}) FROM `{$userstable}`"), 0);
В итоге мы сваливаем работу на mysql, который немного шустрее это сделает и никакого гемора для нас, а после того как узнаем количество общих записей (COUNT(*) mysql кстати берет из памяти) делаем выборку по лимиту


Срочно исправляй:
PHP:
$page=intval($_GET['page'])
А ты SQL инъекцию схватишь.
PHP:
$page=(INT)$_GET['page']
Приведение типов работает быстрее функций (и читабельнее). А вот это более элегантное решение
PHP:
$page = (is_numeric($_GET['p']) && ($_GET['p'] >= 0)) ? $_GET['p']: 0;
 
я бы советовал готовый класс юзать и не париться
 
Статус
В этой теме нельзя размещать новые ответы.
Назад
Сверху