• ベストアンサー

日付、時間の2段階でソート

日付、時間の2段階でソートをしたいのですが、うまくできません。 log.txt に以下の内容が入っています。 <>08/12<>23:15<>あああああああ<> <>08/12<>00:25<>いいいいいいい<> <>02/12<>02:00<>ううううううう<> <>08/12<>22:00<>えええええええ<> <>01/12<>17:52<>おおおおおおお<> それを日付、時間の2段階でソートし以下のように並べ替えたいです。 <>01/12<>17:52<>おおおおおおお<> <>02/12<>02:00<>ううううううう<> <>08/12<>00:25<>いいいいいいい<> <>08/12<>22:00<>えええええええ<> <>08/12<>23:15<>あああああああ<> どなたか教えてください。よろしくお願いします。

質問者が選んだベストアンサー

  • ベストアンサー
  • asock
  • ベストアンサー率70% (7/10)
回答No.3

日付と時間を分離しておくのもよいですが、そのまま秒数のまま保持させておくというのも手です。 <>08/12<>23:15<>あああああああ<>   ↓ <>1155477461<>あああああああ<> 日付・時間→Unix時間の変換は mktime()で行います。 http://au3.php.net/manual/ja/function.mktime.php また、表示時はdate()関数を使用して、date("m/d - H:i) 等して変換します。 もしくは <>08,12,23,15<>あああああああ<> と日付と日時をくっつけて持たせるのもアリでしょう。この場合は後から分解すればよいです。 日付・時間の項目を結合したこと前提で、肝心のソートもいくつか方法があります。 時間がレコード列の先頭にあれば、#2さんの仰るとおりそのままsort()することが出来ます。 そうでない場合はusort()でコールバック関数を適用してソートする方法があります(かなり遅いと思います) http://au3.php.net/manual/ja/function.usort.php $list = file("log.txt"); usort($list, "cmp"); function cmp($a, $b) {  list(,$timeA, ) = explode("<>", $a);  list(,$timeB, ) = explode("<>", $b);  if ($timeA == $timeB) {   return 0;  }  return ($timeA < $timeB) ? -1 : 1; } もう一つの方法として、先に時間を取り出した配列を用意して、array_multisort()を使う方法です。 http://au3.php.net/manual/ja/function.array-multisort.php $list = file("log.txt"); //一旦, 列方向の日付に関する配列を作成 $dates = array(); foreach ($list as $line) {  list(,$date, ) = explode("<>", $list);  array_push($dates, $date); } // ソート array_multisort($dates, SORT_ASC, $list); ご希望の通り「日付」「時間」でデータが分けられた場合の2段階ソートを行う場合も、array_multisort()が利用できます。 $list = file("log.txt"); //一旦, 列方向の日付・時間に関する配列を作成 $dates = array(); $times = array(); foreach ($list as $line) {  list(,$date, $time, ) = explode("<>", $list);  array_push($dates, $date);  array_push($times, $time); } // ソート array_multisort($dates, SORT_ASC, $times, SORT_ASC, $list);

bavarois
質問者

お礼

3番目のがわかりやすかったです。 ありがとうございました。(^o^)b

その他の回答 (3)

  • yambejp
  • ベストアンサー率51% (3827/7415)
回答No.4

改行処理を手抜きしてますが、こんなんで よろしいのでは? <?PHP function cmp($a, $b){ $x=$a[1].$a[3]; $y=$b[1].$b[3]; if($x == $y){ return 0; } return ($x < $y) ? -1 : 1; } $handle = @fopen("log.txt", "r"); if ($handle) { while (!feof($handle)) { $tmp = fgets($handle, 4096); $line[]=split("<>",$tmp); } fclose($handle); } usort($line, "cmp"); foreach($line as $val){ print implode("<>",$val); } ?>

bavarois
質問者

お礼

回答ありがとうございました。 No.3の方の方法で成功しましたので・・・スミマセンm(_ _)m。

  • BLUEPIXY
  • ベストアンサー率50% (3003/5914)
回答No.2

このフォーマットの場合は、そのままソートすればいいと思う。 $data=file("log.txt"); sort($data); print_r($data);

bavarois
質問者

補足

m(_ _)m スミマセン・・・間違えていました。 ↓下のように日付と時間の間に関係ない文字が入っていても2段階でソートする方法が知りたいのです。 <>08/12<>rgrwge<>23:15<>あああああああ<> <>08/12<>4tg4<>00:25<>いいいいいいい<> <>02/12<>g45<>02:00<>ううううううう<> <>08/12<>g4<>22:00<>えええええええ<> <>01/12<>gerge<>17:52<>おおおおおおお<> よろしくお願いします。

回答No.1

日付と時刻の両方を一緒にして mktime か何かで数値化して、それでソートすれば楽勝って気がしますけど。

参考URL:
http://php.s3.to/man/function.mktime.html
bavarois
質問者

補足

もう少し具体的なソート方法を教えてください。 m(_ _)m よろしくお願いします。