2010-05-08 9 views
7

3 기가 텍스트 파일에서 특정 줄을 어떻게 얻을 수 있습니까? 줄은 \ n으로 구분됩니다. 그리고 나는 필요한 모든 라인을 얻을 수 있어야합니다.PHP로 거대한 파일에서 한 줄 가져 오기

어떻게이 작업을 수행 할 수 있습니까? 한 줄만 반환하면됩니다. 그리고 나는 어떤 시스템 호출도 사용하고 싶지 않다.

참고 : bash에서이 작업을 수행하는 방법에 관한 다른 질문이 있습니다. PHP equiv와 비교하고 싶습니다.

업데이트 : 각 행은 전체 길이를 통해 같은 길이입니다. 그것을 위해 내가 생각할 수있는

+0

업데이트 후, 나는 아마도 파일을 다시 계산하기 위해 미리 계산하고 가져 오는 일종의 방법을 생각하고있었습니다. – JavaRocky

+0

데이터베이스없이 데이터베이스를 원합니다. 데이터베이스를 사용할 수 없다고 확신합니까? –

+0

* 시스템 호출이없는 파일을 읽으려고합니다. * ... * 죄송하지만 그냥 사용할 수 없습니다. ('exec '등을 사용하지 않고서 당신은 의미 했습니까?) – salathe

답변

8

, 당신은 그것을 모두 읽을 필요가있을 것이다 of \ n 문자. 그 별명이 방금 그 일을하는 방법을 게시 한 것을 볼 수 있습니다, 그래서 나는 그것을 반복하지 않을 것입니다.

효율적으로 반복적으로 수행하려면 인덱스를 만들어야합니다. 특정 (또는 모든) 행 번호에 대해 알려진 파일 위치를 한 번 저장 한 다음 fseek을 사용하여 올바른 위치를 탐색하는 데 사용할 수 있습니다.

편집 : 각 줄의 길이가 같으면 색인이 필요하지 않습니다.

$myfile = fopen($fileName, "r"); 
fseek($myfile, $lineLength * $lineNumber); 
$line = fgets($myfile); 
fclose($myfile); 

이 예제에서는 줄 번호가 0이므로, 먼저 줄 번호를 뺄 필요가 있습니다. 줄 길이는 \n 문자를 포함합니다.

+0

그러나 그의 파일이 거대한 것임을 감안할 때, fseek는 여전히 상당한 시간을 허비하지 않을 것입니다. – Pacerier

+0

@Pacerier : 아니요. 끝나기 시작하는 모든 데이터를 읽을 필요가 없으므로 아닙니다. 파일은 임의 액세스입니다. – Thorarin

1

유일한 방법은 다음과 같이 될 것이다 : 당신이 x 개의 발생 때까지 파일에 인덱스의 일종을 유지하지 않고

function getLine($fileName, $num) { 
    $fh = fopen($fileName, 'r'); 

    for ($i = 0; $i < $num && ($line = fgets($fh)); ++$i); 

    return $line; 
} 
0

, 어떻게 3 공연 텍스트 파일에서 한 줄을 당길 필요가있다 오지? 성능에 문제가 있습니까? 아니면 여유로운 속도로 달릴 수 있습니까? 시간이 다른 시점에서이 파일에서 많은 행을 가져와야하는 경우이 데이터를 일종의 DB에 저장하는 것이 좋습니다. SQLite 아마도 여기에 귀하의 친구가 아주 간단하지만 많은 스크립트/사람들이 한 번에 그것을 액세스와 함께 위대하지.

8

문제의 약간의 논의가 더 언급은 '한 줄'이 (번호 등, 그 안에 어떤 값으로) 참조 할 방법의 사용은 금지되어 있으므로 아래 당신이있어 무엇인지에 단지 추측 이 없이.

오브젝트를 사용하는 것을 반대하지 않고 (아마도 '너무 높은 레벨'일 수 있음) 오프셋을 기준으로 라인을 참조하려는 경우 SplFileObject (PHP 5.1.0부터 사용 가능)을 사용할 수 있습니다. 다음과 같은 기본 예제를 참조하십시오 :

특정 방법 ( seek가) 파일을 줄 단위를 스캔을 필요로
$file = new SplFileObject('myreallyhugefile.dat'); 
$file->seek(12345689); // seek to line 123456790 
echo $file->current(); // or simply, echo $file 

. 그러나 모든 줄의 길이가 같다고 가정하면 fseek을 사용하여 에 훨씬 더 빨리 도달 할 수 있습니다..

$line_length = 1024; // each line is 1 KB line 
$file->fseek($line_length * 1234567); // seek lots of bytes 
echo $file->current(); // echo line 1234568 
관련 문제