대용량 파일을 한 줄씩 읽는 방법
파일을 한 줄 한 줄 읽고 싶은데 메모리에 완전히 로드하지 않고 읽고 싶습니다.
파일이 너무 커서 메모리에서 열 수 없습니다.열려고 하면 항상 메모리 오류가 발생합니다.
파일 사이즈는 1GB입니다.
를 사용할 수 있습니다.fgets()
파일을 한 줄씩 읽는 함수:
$handle = fopen("inputfile.txt", "r");
if ($handle) {
while (($line = fgets($handle)) !== false) {
// process the line read.
}
fclose($handle);
}
if ($file = fopen("file.txt", "r")) {
while(!feof($file)) {
$line = fgets($file);
# do same stuff with the $line
}
fclose($file);
}
파일에 객체 지향 인터페이스 클래스를 사용할 수 있습니다. http://php.net/manual/en/splfileobject.fgets.php (PHP 5 > = 5.1.0)
<?php
$file = new SplFileObject("file.txt");
// Loop until we reach the end of the file.
while (!$file->eof()) {
// Echo one line from the file.
echo $file->fgets();
}
// Unset the file to call __destruct(), closing the file handle.
$file = null;
사용하고 싶은 경우foreach
대신while
큰 파일을 열 때는 아마 캡슐화해야 할 필요가 있을 겁니다.while
전체 파일을 메모리에 로드하지 않도록 제너레이터 내부에서 루프를 실행합니다.
/**
* @return Generator
*/
$fileData = function() {
$file = fopen(__DIR__ . '/file.txt', 'r');
if (!$file) {
return; // die() is a bad practice, better to use return
}
while (($line = fgets($file)) !== false) {
yield $line;
}
fclose($file);
};
다음과 같이 사용합니다.
foreach ($fileData() as $line) {
// $line contains current line
}
이렇게 하면 foreach() 내의 개별 파일 행을 처리할 수 있습니다.
참고: 생성기에는 >= PHP 5.5가 필요합니다.
이 있습니다.file()
파일에 포함된 행의 배열을 반환하는 함수입니다.
foreach(file('myfile.txt') as $line) {
echo $line. "\n";
}
모든 답변에 명백한 답은 없었다.
PHP에는 바로 그 목적을 위해 만들어진 깔끔한 스트리밍 딜리미터 파서가 있습니다.
$fp = fopen("/path/to/the/file", "r");
while (($line = stream_get_line($fp, 1024 * 1024, "\n")) !== false) {
echo $line;
}
fclose($fp);
버퍼링 기술을 사용하여 파일을 읽습니다.
$filename = "test.txt";
$source_file = fopen( $filename, "r" ) or die("Couldn't open $filename");
while (!feof($source_file)) {
$buffer = fread($source_file, 4096); // use a buffer of 4KB
$buffer = str_replace($old,$new,$buffer);
///
}
foreach (new SplFileObject(__FILE__) as $line) {
echo $line;
}
이것이, 매우 큰 파일(최대 100 G로 테스트 완료)로 관리하는 방법입니다.fgets()보다 빠릅니다.
$block =1024*1024;//1MB or counld be any higher than HDD block_size*2
if ($fh = fopen("file.txt", "r")) {
$left='';
while (!feof($fh)) {// read the file
$temp = fread($fh, $block);
$fgetslines = explode("\n",$temp);
$fgetslines[0]=$left.$fgetslines[0];
if(!feof($fh) )$left = array_pop($lines);
foreach ($fgetslines as $k => $line) {
//do smth with $line
}
}
}
fclose($fh);
(!fe of...)을 조심하라.fgets()'의 경우 fgets는 에러(returnfing false)를 수신하여 파일 끝에 도달하지 않고 영원히 루프할 수 있습니다.codaddict는 가장 정확하지만 fgets 루프가 종료되면 feof를 확인합니다.그렇지 않으면 오류가 발생한 것입니다.
SplFileObject는 대용량 파일을 처리할 때 유용합니다.
function parse_file($filename)
{
try {
$file = new SplFileObject($filename);
} catch (LogicException $exception) {
die('SplFileObject : '.$exception->getMessage());
}
while ($file->valid()) {
$line = $file->fgets();
//do something with $line
}
//don't forget to free the file handle.
$file = null;
}
이 질문에 대한 일반적인 해결책 중 하나에서 새 줄 문자에 문제가 발생합니다.심플하면 쉽게 고칠 수 있습니다.str_replace
.
$handle = fopen("some_file.txt", "r");
if ($handle) {
while (($line = fgets($handle)) !== false) {
$line = str_replace("\n", "", $line);
}
fclose($handle);
}
<?php
echo '<meta charset="utf-8">';
$k= 1;
$f= 1;
$fp = fopen("texttranslate.txt", "r");
while(!feof($fp)) {
$contents = '';
for($i=1;$i<=1500;$i++){
echo $k.' -- '. fgets($fp) .'<br>';$k++;
$contents .= fgets($fp);
}
echo '<hr>';
file_put_contents('Split/new_file_'.$f.'.txt', $contents);$f++;
}
?>
어레이 반환 시 읽기 기능
function read_file($filename = ''){
$buffer = array();
$source_file = fopen( $filename, "r" ) or die("Couldn't open $filename");
while (!feof($source_file)) {
$buffer[] = fread($source_file, 4096); // use a buffer of 4KB
}
return $buffer;
}
언급URL : https://stackoverflow.com/questions/13246597/how-to-read-a-large-file-line-by-line
'programing' 카테고리의 다른 글
Javascript 'atob'과 'btoa'는 왜 그렇게 이름 붙여졌을까? (0) | 2022.09.08 |
---|---|
MySQL SELECT AS는 두 열을 하나로 결합합니다. (0) | 2022.09.08 |
phpmyadmin 오류 해결 방법 (0) | 2022.09.08 |
bash 스크립트가 MariaDB 서비스 상태를 올바르게 제공하지 않음 (0) | 2022.09.06 |
어레이를 청크로 분할하다 (0) | 2022.09.06 |