PHP:从文件中读取特定行

发布于 2024-11-03 10:52:08 字数 299 浏览 5 评论 0原文

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

foo  
foo2

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

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

..但我需要第二行。

任何帮助将不胜感激

I'm trying to read a specific line from a text file using php.
Here's the text file:

foo  
foo2

How would I get the content of the second line using php?
This returns the first line:

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

..but I need the second.

Any help would be greatly appreciated

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(12

满栀 2024-11-10 10:52:08
$myFile = "4-24-11.txt";
$lines = file($myFile);//file in to an array
echo $lines[1]; //line 2

file — 将整个文件读入数组

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

file — Reads entire file into an array

帅哥哥的热头脑 2024-11-10 10:52:08

天哪我缺少 7 名代表来发表评论。这是@Raptor 的& @Tomm 的评论,因为这个问题在谷歌搜索结果中仍然显示得很高。

他是完全正确的。对于小文件 file($file); 完全没问题。对于大文件来说,b/c php 数组会疯狂地消耗内存,这完全是矫枉过正。

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

$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

由于还没有人提到它,所以我尝试了 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

这是在我的 Win7 桌面上,所以它不代表生产环境,但仍然......有很大区别。

omg I'm lacking 7 rep to make comments. This is @Raptor's & @Tomm's comment, since this question still shows up way high in google serps.

He's exactly right. For small files file($file); is perfectly fine. For large files it's total overkill b/c php arrays eat memory like crazy.

I just ran a tiny test with a *.csv with a file size of ~67mb (1,000,000 lines):

$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

And since noone mentioned it yet, I gave the SplFileObject a try, which I actually just recently discovered for myself.

$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

This was on my Win7 desktop so it's not representative for production environment, but still ... quite the difference.

挽你眉间 2024-11-10 10:52:08

如果您想这样做...

$line = 0;

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

或者,使用 file( 打开它) 并使用 [1] 为该行添加下标。

If you wanted to do it that way...

$line = 0;

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

Alternatively, open it with file() and subscript the line with [1].

云归处 2024-11-10 10:52:08

我会使用 SplFileObject 类...

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

I would use the SplFileObject class...

$file = new SplFileObject("filename");
if (!$file->eof()) {
     $file->seek($lineNumber);
     $contents = $file->current(); // $contents would hold the data from line x
}
物价感观 2024-11-10 10:52:08

您可以使用以下命令获取文件中的所有行

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

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


print_r($lines);

以及第二行的 $lines[1]

you can use the following to get all the lines in the file

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

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


print_r($lines);

and $lines[1] for your second line

脱离于你 2024-11-10 10:52:08
$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);
$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);
兔姬 2024-11-10 10:52:08

这个问题现在已经很老了,但是对于处理非常大文件的任何人来说,这里有一个解决方案,不涉及读取前面的每一行。这也是在我的案例中,对于大约 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
?>

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

This question is quite old by now, but for anyone dealing with very large files, here is a solution that does not involve reading every preceding line. This was also the only solution that worked in my case for a file with ~160 million lines.

<?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
?>

It works by opening the file without reading anything, then moving the pointer instantly to a random position, reading up to 4096 characters from that point, then grabbing the first complete line from that data.

笑梦风尘 2024-11-10 10:52:08

如果您在 Linux 上使用 PHP,您可以尝试以下方法来读取文本,例如第 74 行和第 159 行之间的文本:

$text = shell_exec("sed -n '74,159p' path/to/file.log");

如果您的文件很大,则此解决方案很好。

If you use PHP on Linux, you may try the following to read text for example between 74th and 159th lines:

$text = shell_exec("sed -n '74,159p' path/to/file.log");

This solution is good if your file is large.

酒废 2024-11-10 10:52:08

您必须循环文件直到文件末尾。

  while(!feof($file))
  {
     echo fgets($file). "<br />";
  }
  fclose($file);

You have to loop the file till end of file.

  while(!feof($file))
  {
     echo fgets($file). "<br />";
  }
  fclose($file);
や三分注定 2024-11-10 10:52:08

我喜欢 daggett 答案,但如果您的文件不够大,您可以尝试另一种解决方案。

$file = __FILE__; // Let's take the current file just as an example.

$start_line = __LINE__ -1; // The same with the line what we look for. Take the line number where $line variable is declared as the start.

$lines_to_display = 5; // The number of lines to display. Displays only the $start_line if set to 1. If $lines_to_display argument is omitted displays all lines starting from the $start_line.

echo implode('', array_slice(file($file), $start_line, lines_to_display));

I like daggett answer but there is another solution you can get try if your file is not big enough.

$file = __FILE__; // Let's take the current file just as an example.

$start_line = __LINE__ -1; // The same with the line what we look for. Take the line number where $line variable is declared as the start.

$lines_to_display = 5; // The number of lines to display. Displays only the $start_line if set to 1. If $lines_to_display argument is omitted displays all lines starting from the $start_line.

echo implode('', array_slice(file($file), $start_line, lines_to_display));
黎夕旧梦 2024-11-10 10:52:08

使用stream_get_line:stream_get_line — 从流资源获取到给定分隔符的行
来源: http://php.net/manual/en/function.stream -get-line.php

Use stream_get_line: stream_get_line — Gets line from stream resource up to a given delimiter
Source: http://php.net/manual/en/function.stream-get-line.php

若能看破又如何 2024-11-10 10:52:08

您可以尝试循环直到您想要的行,而不是 EOF,并每次将变量重置为该行(而不是添加到它)。在你的例子中,第二行是 EOF。 (在我下面的代码中,for 循环可能更合适)。

这样整个文件就不在内存中了;缺点是需要花费一些时间才能浏览文件直到您想要的位置。

<?php 
$myFile = "4-24-11.txt";
$fh = fopen($myFile, 'r');
$i = 0;
while ($i < 2)
 {
  $theData = fgets($fh);
  $i++
 }
fclose($fh);
echo $theData;
?>

You could try looping until the line you want, not the EOF, and resetting the variable to the line each time (not adding to it). In your case, the 2nd line is the EOF. (A for loop is probably more appropriate in my code below).

This way the entire file is not in the memory; the drawback is it takes time to go through the file up to the point you want.

<?php 
$myFile = "4-24-11.txt";
$fh = fopen($myFile, 'r');
$i = 0;
while ($i < 2)
 {
  $theData = fgets($fh);
  $i++
 }
fclose($fh);
echo $theData;
?>
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文