単二電池

以前DBを使用しないページングについてお教えいただいた者です。

少し改良して降順ソートを出来るようになったのですが、
リスト表示の際にある条件に一致したもののみを表示する場合の
やり方が分かりません。。。

現在は以下のようになっています。

■sample.csv
no0001,あああああ,20050101,ON
no0002,いいいいい,20050102,OFF
略)
no0020,ととととと,20050120,OFF

■index.php
(800字オーバーしてしまうので、省略しています。)
//ファイルを配列に格納
$rec = file("sample.csv");
//レコード数を取得して、最後尾の行番号を取得
$rec_number = sizeof($rec) -1;

//ページ範囲を出力
for ( $i = $rec_number-$page*$max; $i > $rec_number-$page*$max-$max; $i -- ) {
$data = explode(",","$rec[$i]");
if ($data[3]==("ON") && $data[2]<=date("Ymd")) {
print $data[0].("<br>");
print $data[1].("<br>");
print $data[2].("<br><br>\n");
}
}
print "<a href=\"?page=".($page+1)."\">次のページへ</a>\n";
?>

CSVの各行の[3]が
「ON」となっていれば表示し、
「OFF」となっていれば表示しないようにし、
また、[2]が
今日以降の日付であれば表示しないようにしたいのですが、
for文の中に上記のようなif文を使ってしまうとオカシナことに
なってしまいます。
(no0020が抜けただけで1ページ目に9件しか表示されません。本当は
no0020が抜けたので、no0010までの10件を表示させたいのです。)

根本的な部分が間違っているような気がするのですが、
どのような考え方で作れば良いのか分かりません。

また皆様のお力をお貸しください。
宜しくお願いします。

A 回答 (3件)

> 次のページへ渡していないからだと思うのですが、


> これはPOSTなりGETで参照渡しをするのでしょうか?
 今ページ番号って渡してる? おそらくそれが最終的に$pageになるのだと思うのだが。
 今、「有効な行を数えて」10行分きちんと出す事ができた。ここでちょっと考えて欲しい。2ページ目に表示するのは「CSVの11行目から」だろうか?
 否、「CSVを先頭から全部舐めていって、有効な行を10行分(←1ページ目の分)捨てた後に、最初に出てきた有効な行」だ。これが、前回の回答で私が「頭出し」と言った部分だ。
 という訳で、次の関数を作りましょう。クラスにしても良いだろう。

class MyRecords {
var recnum; // int
var recmax; // int
var records; // array
int initCsvData(array recs); // file関数で読み込んだ行データを引数に、現在行などを初期化。
array getNextLine(); // 次の有効な行を返す。
}

このような下請けルーチンを作ることで、メインルーチンはこんなに簡単になる。

$recs = new MyRecords();
$recs->initCsvData($rec); // CSVデータをセット
for($i = 0; $i < $page * $max; $i++) { // 「ページ数×ページあたりの行数」分だけ
$recs->getNextLine(); // 捨てる。
}
for($i = 0; $i < $max; $i++) { // 「ページあたりの行数」分だけ
if(!$arr = $recs->getNextLine()) break; // もうデータが無ければループ終了(最後のページとなる)
// ~~行をHTMLに吐き出す~~
}

とても見通しが良くなったっしょ。こげな感じでどうでっしゃろ。
    • good
    • 0
この回答へのお礼

お返事ありがとうございます。
ご説明がとても分かりやすく、理論的に理解は
出来たのですが、初心者のため関数の部分が読めません・・・(涙

下記のように貼り付けてみたのですが、
13行目にエラーが出てしまいます。
「Parse error: parse error, expecting `T_VARIABLE'」

<?php
// 1ページに表示する最大数
$max = 10;
// 現在のページ数を取得
$page=$_GET['page'];
if ( $page == "" ) {
$page = 0;
}
//ファイルを配列に格納
$rec = file("sample.csv");

class MyRecords {
var recnum; // int
var recmax; // int
var records; // array
int initCsvData(array recs); // file関数で読み込んだ行データを引数に、現在行などを初期化。
array getNextLine(); // 次の有効な行を返す。
}

$recs = new MyRecords();
$recs->initCsvData($rec); // CSVデータをセット
for($i = 0; $i < $page * $max; $i++) { // 「ページ数×ページあたりの行数」分だけ
$recs->getNextLine(); // 捨てる。
}
for($i = 0; $i < $max; $i++) { // 「ページあたりの行数」分だけ
if(!$arr = $recs->getNextLine()) break; // もうデータが無ければループ終了(最後のページとなる)
// ~~行をHTMLに吐き出す~~
print <<<HTML
$recs[0].("<br>");
$recs[1].("<br>");
$recs[2].("<br><br>");
HTML;
}
?>

何度もお手数をお掛けし申し訳ありません。
宜しくお願いいたします。

お礼日時:2005/02/02 19:17

continueしてやるのはどうでしょうか?



for ( $i = $rec_number-$page*$max; $i > $rec_number-$page*$max-$max; $i -- ) {
$data = explode(",","$rec[$i]");
if ($data[3]==("ON") && $data[2]<=date("Ymd")) {
print $data[0].("<br>");
print $data[1].("<br>");
print $data[2].("<br><br>\n");
}else{
continue;
}
}
    • good
    • 0
この回答へのお礼

お返事ありがとうございます。

しかし、continue を使っても、結果は同じで、
OFFの部分と本日の日付を越えた部分を抜いた
10行以下の出力結果が表示されただけでした・・・。

お手数ですが他のもヒントがありましたらお教えください。宜しくお願いいたします。

お礼日時:2005/02/02 16:16

for ( $i = $rec_number-$page*$max; $i > $rec_number-$page*$max-$max; $i -- ) {


ここが問題だね。中をよく見てみると、「出力しようがしまいが$max回ループする」事になる。
という訳で、「$max行出力するまでループ」という方法に変えてあげましょう。
そうだなぁ。あまりごちゃごちゃ変えるのもあれなので、こんなのはどうだろう。

$outputline = 0;
$i = $rec_number-$page*$max; // ここもおかしいよね。$rec[$i]を先頭から1行ずつ舐めていって、条件に合致する行数を数えていって頭だしをしないといけない。
while($outputline < max || $i <= $rec_number) {
$data = explode(",", $rec[$i++]);
if ($data[3]==("ON") && $data[2]<=date("Ymd")) {
print $data[0].("<br>");
print $data[1].("<br>");
print $data[2].("<br><br>\n");
outputline++; // 行を出力したので1行増やす。これが$maxまで到達すると1ページ分。
}
}
    • good
    • 0
この回答へのお礼

お返事ありがとうございます。

しかしお教えいただいたやり方を
とりあえず昇順ソートで試してみたのですが、
出力結果が

●1ページ目
no0001,あああああ,20050101,ON
no0003,ううううう,20050103,ON
no0004,えええええ,20050104,ON
no0005,おおおおお,20050105,ON
no0006,かかかかか,20050106,ON
no0007,ききききき,20050107,ON
no0008,くくくくく,20050108,ON
no0009,けけけけけ,20050109,ON
no0010,こここここ,20050110,ON
no0011,さささささ,20050111,ON
と10行分表示されるのですが、

●2ページ目
no0011,さささささ,20050111,ON
no0012,ししししし,20050112,ON
略)

とCSVデータの10行目から読み込みを
始めてしまいます。

恐らく、お教えいただいた
> $i = $rec_number-$page*$max; // ここもおかしいよね。
> $rec[$i]を先頭から1行ずつ舐めていって、条件に合致する行数を
> 数えていって頭だしをしないといけない。
ココを次のページへ渡していないからだと思うのですが、
これはPOSTなりGETで参照渡しをするのでしょうか?

度々お手数ですが、宜しくお願いいたします。

お礼日時:2005/02/02 16:13

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!