2012-06-03 3 views
0

Я создаю сценарий разбивки на страницы, и мне нужно получить первый и последний результаты в запросе базы данных, чтобы я мог определить, какие результаты появляются, когда пользователь нажимает на страницу, на которую нужно перейти. Это код, который я имею в минуту:Как получить первый и последний результаты запроса?

// my database connection is opened 

// this gets all of the entries in the database 
$q = mysql_query("SELECT * FROM my_table ORDER BY id ASC"); 
$count = mysql_num_rows($q); 
// this is how many results I want to display 
$max = 2; 
// this determines how many pages there will be 
$pages = round($count/$max,0); 
// this is where I think my script goes wrong 
// I want to get the last result of the first page 
// or the first result of the previous page 
// so the query can start where the last query left off 
// I've tried a few different things to get this script to work 
// but I think that I need to get the first or last result of the previous page 
// but I don't know how to. 
$get = $_GET['p']; 
$pn = $_GET['pn']; 
$pq = mysql_query("SELECT * FROM my_table ORDER BY id ASC LIMIT $max OFFSET $get"); 

// my query results appear 

if(!$pn) { 
    $pn = 1; 
} 
echo "</table><br /> 
Page $pn of $pages<br />"; 
for($p = 1;$p<=$pages;$p++) { 
    echo "<a href='javascript:void(0);' onclick='nextPage($max, $p);' title='Page $p'>Page $p</a> "; 
} 
+2

** Ваш код уязвим для SQL-инъекции. ** Вы * действительно * должны использовать подготовленные инструкции, в которые вы передаете переменные в качестве параметров, которые не оцениваются для SQL. Если вы не знаете, о чем я говорю, или как это исправить, прочитайте рассказ о [Bobby Tables] (http://bobby-tables.com). – eggyal

+1

Кроме того, прекратите писать новый код с древним расширением MySQL: он больше не поддерживается, и сообщество начало процесс [устаревания] (http://news.php.net/php.internals/53799). Вместо этого вы должны использовать либо улучшенное расширение [MySQLi] (http://php.net/mysqli), либо уровень абстракции [PDO] (http://php.net/pdo). – eggyal

+0

Непонятно, в чем вопрос. –

ответ

3

Думаю, у вас мало проблем, но я пытаюсь решить их для вас. Во-первых, как сказано выше, вы используете код, который он уязвим для SQL-инъекции. Позаботьтесь об этом - вы можете использовать PDO, что так же просто, как расширение MySQL, и избавит вас от многих проблем (например, инъекции).

Но в код, позволяет пройти через него:

  1. Вы должны спросить DB, чтобы получить количество строк, а не с помощью функции MySQL, это гораздо более эффективно, так что используйте SELECT count(*) FROM mytable.
  2. Для $pages использования потолке(), как вы хотите, чтобы все строки должны быть напечатаны, если у вас есть $max 5 и иметь 11 строк, вокруг будет сделать $pages 2, где вы на самом деле хотите 3 (последняя страница содержит только, что последний 11-й ряд)
  3. в LIMIT вы хотите LIMIT row_count OFFSET offset. Вы можете рассчитать смещение от номера страницы, так: $max = row_count, но $offset = ($max * $page) - $max. В вашем коде, если $get находится непосредственно на странице, это означает, что вы получите $ get'th строку (не уверен, хотя то, что происходит в вашем JS СледующаяСтраница. Голые в виду, что не все используют JavaScript.)

I подготовили простой пример здесь, который использует PDO, может быть, это дает вам представление о том, насколько просто он использует PDO.

выбирающих строки показывает пример того, как поставить параметры в SQL, это было бы совершенно безопасно в этом случае состоянии, 'SELECT * FROM pseudorows LIMIT '.$start.','.$max от Я хотел сделать пример того, как легко (и затем безопасно):

// DB config 
$DB_NAME = 'test'; 
$DB_USER = 'test'; 
$DB_PASSWD = 'test'; 

    // make connection 
try { 
    $DB_CONN = new PDO("mysql:host=localhost;dbname=".$DB_NAME, $DB_USER, $DB_PASSWD); 
    $DB_CONN->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); 
} catch (PDOException $e) { 
    die($e); 
} 

// lets say user param 'p' is page, we cast it int, just to be safe 
$page = (int) (isset($_GET['p'])?$_GET['p']:1); 
// max rows in page 
$max = 20; 

// first select count of all rows in the table 
$stmt = $DB_CONN->prepare('SELECT count(*) FROM pseudorows'); 
$stmt->execute(); 
if($value = $stmt->fetch()) { 
    // now we know how many pages we must print in pagination 
    // it's $value/$max = pages 
    $pages = ceil($value[0]/$max); 

    // now let's print this page results, we are on $page page 
    // we start from position max_rows_in_page * page_we_are_in - max_rows_in_page 
    // (as first page is 1 not 0, and rows in DB start from 0 when LIMITing) 
    $start = ($page * $max) - $max; 
    $stmt = $DB_CONN->prepare('SELECT * FROM pseudorows LIMIT :start,:max'); 
    $stmt->bindParam(':start',$start,PDO::PARAM_INT); 
    $stmt->bindParam(':max', $max,PDO::PARAM_INT); 
    $stmt->execute(); 

    // simply just print rows 
    echo '<table>'; 
    while($row = $stmt->fetch()) { 
     echo '<tr><td>#'.$row['id'].'</td><td>'.$row['title'].'</td></tr>'; 
    } 
    echo '</table>'; 

    // let's show pagination 
    for($i=1;$i<=$pages;$i++) { 
     echo '[ <a href="?p='.$i.'">'.$i.'</a> ]'; 
    } 
} 
+0

Это отлично поработало, спасибо! – JustSomeGuy

0

mysql_fetch_array возвращает ассоциативный массив

означает, что вы можете использовать reset и end, чтобы получить первые и последние результаты:

$pqa = mysql_fetch_array($pq); 
$first = reset($pqa); 
$last = end($pqa); 

Я не вижу, как вы планируете использовать фактические результаты, просто номера страниц должны быть достаточными для разбивки на страницы.

По-прежнему надеемся, что это поможет. И да, переход на mysqli, поэтому ваш код не устареет.

Смежные вопросы