开发者

PHP read last few lines of the file without copying the entire file to memory

W开发者_如何学运维ell you know I can use this:

<?php
$myfile = 'myfile.txt';
$command = "tac $myfile > /tmp/myfilereversed.txt";
exec($command);
$currentRow = 0;
$numRows = 20;  // stops after this number of rows
$handle = fopen("/tmp/myfilereversed.txt", "r");
while (!feof($handle) && $currentRow <= $numRows) {
   $currentRow++;
   $buffer = fgets($handle, 4096);
   echo $buffer."<br>";
}
fclose($handle);
?>

But doesn't it copy the whole file to memory?

A better approach maybe fread() but it uses the bytes so might also not be the a good approach too.

My file can go into around 100MB so I want it.


If you're already doing stuff on the command line, why not use tail directly:

$myfile = 'myfile.txt';
$command = "tail -20 $myfile";
$lines = explode("\n", shell_exec($command));

Not tested, but should work without PHP having to read the whole file.


Try applying this logic as it might help: read long file in reverse order fgets


Most f*()-functions are stream-based and therefore will only read into memory, what should get read.

As fas as I understand you want to read the last $numRows line from a file. A maybe naive solution

$result = array();
while (!feof($handle)) {
  array_push($result, fgets($handle, 4096));
  if (count($result) > $numRows) array_shift($result);
}

If you know (lets say) the maximum line length, you can try to guess a position, that is nearer at the end of the file, but before at least $numRows the end

$seek = $maxLineLength * ($numRows + 5); // +5 to assure, we are not too far
fseek($handle, -$seek, SEEK_END);
// See code above
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜