PHP:从文件中读取特定行

San*_*oid 54 php file line

我正在尝试使用php从文本文件中读取特定行.这是文本文件:

foo  
foo2
Run Code Online (Sandbox Code Playgroud)

如何使用php获取第二行的内容?这将返回第一行:

<?php 
$myFile = "4-24-11.txt";
$fh = fopen($myFile, 'r');
$theData = fgets($fh);
fclose($fh);
echo $theData;
?>
Run Code Online (Sandbox Code Playgroud)

..但我需要第二个.

任何帮助将不胜感激

小智 82

$myFile = "4-24-11.txt";
$lines = file($myFile);//file in to an array
echo $lines[1]; //line 2
Run Code Online (Sandbox Code Playgroud)

file - 将整个文件读入数组

  • 如果文件大小很大,这个解决方案会很慢并占用大量内存. (69认同)
  • 将整个文件读入内存只是为了得到第二行?在某些情况下,我会说这是一个灾难的处方(见Raptor的评论). (13认同)
  • 仍然有 40 多个赞成票?我会说这还不算太糟糕;-) (3认同)
  • 注意:那应该是`$ lines [1]` (2认同)

nim*_*eun 34

omg我缺少7位代表发表评论.这是@ Raptor's&@ Tomm的评论,因为这个问题在谷歌服务中仍然显示出很高的水平.

他是完全正确的.对于小文件file($file);是完全正常的.对于大文件来说,它总是过度使用b/c php数组会像疯了一样吃内存.

我刚刚用*.csv进行了一次小测试,文件大小约为67mb(1,000,000行):

$t = -microtime(1);
$file = '../data/1000k.csv';
$lines = file($file);
echo $lines[999999]
    ."\n".(memory_get_peak_usage(1)/1024/1024)
    ."\n".($t+microtime(1));
//227.5
//0.22701287269592
//Process finished with exit code 0
Run Code Online (Sandbox Code Playgroud)

既然没有人提到它,我SplFileObject试了一下,实际上我最近刚刚为自己找到了.

$t = -microtime(1);
$file = '../data/1000k.csv';
$spl = new SplFileObject($file);
$spl->seek(999999);
echo $spl->current()
    ."\n".(memory_get_peak_usage(1)/1024/1024)
    ."\n".($t+microtime(1));
//0.5
//0.11500692367554
//Process finished with exit code 0
Run Code Online (Sandbox Code Playgroud)

这是在我的Win7桌面上,因此它不具备生产环境的代表性,但仍然......相当不同.

  • 请记住,`SplFileObject` 会锁定文件。因此,当不再需要类时将其设为 null(例如`$spl = null;`),否则您将被拒绝对该文件进行其他一些操作 - 删除、重命名、在类外访问等。 (2认同)

ale*_*lex 18

如果你想这样做......

$line = 0;

while (($buffer = fgets($fh)) !== FALSE) {
   if ($line == 1) {
       // This is the second line.
       break;
   }   
   $line++;
}
Run Code Online (Sandbox Code Playgroud)

或者,打开它file()并使用下标[1].


Phi*_*hil 11

我会使用SplFileObject类...

$file = new SplFileObject("filename");
if (!$file->eof()) {
     $file->seek($lineNumber);
     $contents = $file->current(); // $contents would hold the data from line x
}
Run Code Online (Sandbox Code Playgroud)


bal*_*anv 9

您可以使用以下内容获取文件中的所有行

$handle = @fopen('test.txt', "r");

if ($handle) { 
   while (!feof($handle)) { 
       $lines[] = fgets($handle, 4096); 
   } 
   fclose($handle); 
} 


print_r($lines);
Run Code Online (Sandbox Code Playgroud)

$lines[1]为你的第二行


Pho*_*nix 6

$myFile = "4-21-11.txt";
$fh = fopen($myFile, 'r');
while(!feof($fh))
{
    $data[] = fgets($fh);  
    //Do whatever you want with the data in here
    //This feeds the file into an array line by line
}
fclose($fh);
Run Code Online (Sandbox Code Playgroud)

  • 顺便说一下,如果你可能正在使用任何大文件,那么在实践中不建议将整个文件输入到数组中,例如使用`file()`或`file_get_contents()`.对于小文件,它工作得很好. (3认同)

can*_*ope 5

这个问题现在已经很老了,但是对于处理非常大文件的任何人来说,这里有一个解决方案,不涉及读取前面的每一行。这也是在我的案例中,对于大约 1.6 亿行的文件有效的唯一解决方案。

<?php
function rand_line($fileName) {
    do{
        $fileSize=filesize($fileName);
        $fp = fopen($fileName, 'r');
        fseek($fp, rand(0, $fileSize));
        $data = fread($fp, 4096);  // assumes lines are < 4096 characters
        fclose($fp);
        $a = explode("\n",$data);
    }while(count($a)<2);
    return $a[1];
}

echo rand_line("file.txt");  // change file name
?>
Run Code Online (Sandbox Code Playgroud)

它的工作原理是打开文件而不读取任何内容,然后立即将指针移动到随机位置,从该点读取最多 4096 个字符,然后从该数据中抓取第一个完整行。