Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

fseek() by line, not bytes?

Tags:

file

php

fgets

I have a script that parses large files line by line. When it encounters an error that it can't handle, it stops, notifying us of the last line parsed.

Is this really the best / only way to seek to a specific line in a file? (fseek() is not usable in my case.)

<?php

for ($i = 0; $i < 100000; $i++)
    fgets($fp); // just discard this

I don't have a problem using this, it is fast enough - it just feels a bit dirty. From what I know about the underlying code, I don't imagine there is a better way to do this.

like image 989
jasonbar Avatar asked Aug 27 '10 22:08

jasonbar


2 Answers

An easy way to seek to a specific line in a file is to use the SplFileObject class, which supports seeking to a line number (seek()) or byte offset (fseek()).

$file = new SplFileObject('myfile.txt');
$file->seek(9999);     // Seek to line no. 10,000
echo $file->current(); // Print contents of that line

In the background, seek() just does what your PHP code did (except, in C code).

like image 68
salathe Avatar answered Oct 04 '22 21:10

salathe


If you only have the line number to go on, there is no other method of finding the line. Files are not line based (or even character based), so there is no way to simply jump to a specific line in a file.

There might be other ways of reading the lines in the file that might be slightly faster, like reading larger chunks of the file into a buffer and read lines from that, but you could only hope for it to be a few percent faster. Any method to find a specific line in a file still has to read all data up to that line.

like image 21
Guffa Avatar answered Oct 04 '22 20:10

Guffa