[英]Delete a specific line in a TXT file
我有一个.txt文件,其中包含数百万行文本
下面的代码删除.txt文件中的特定行(.com域)。 但是大文件不能做:(
<?php
$fname = "test.txt";
$lines = file($fname);
foreach($lines as $line) if(!strstr($line, ".com")) $out .= $line;
$f = fopen($fname, "w");
fwrite($f, $out);
fclose($f);
?>
我想删除某些行并将其放在另一个文件中
例如,网站的域名列表。 剪切.com域并将其粘贴到另一个文件中...
这是一种使用http://php.net/manual/en/class.splfileobject.php并使用临时文件的方法。
$fileName = 'whatever.txt';
$linesToDelete = array( 3, 5 );
// Working File
$file = new SplFileObject( $fileName, 'a+' );
$file->flock( LOCK_EX );
// Temp File
$temp = new SplTempFileObject( 0 );
$temp->flock( LOCK_EX );
// Wite the temp file without the lines
foreach( $file as $key => $line )
{
if( in_array( $key + 1, $linesToDelete ) === false )
{
$temp->fwrite( $line );
}
}
// Write Back to the main file
$file->ftruncate(0);
foreach( $temp as $line )
{
$file->fwrite( $line );
}
$file->flock( LOCK_UN );
$temp->flock( LOCK_UN );
虽然这可能很慢,但是在Windows xampp安装程序上,一个40兆的文件和140000行的文件需要2.3秒。 可以通过写入临时文件并执行文件移动来加快速度,但是我不想在您的环境中踩踏文件权限。
编辑:使用重命名/移动而不是第二次写入的解决方案
$fileName = __DIR__ . DIRECTORY_SEPARATOR . 'whatever.txt';
$linesToDelete = array( 3, 5 );
// Working File
$file = new SplFileObject( $fileName, 'a+' );
$file->flock( LOCK_EX );
// Temp File
$tempFileName = tempnam( sys_get_temp_dir(), rand() );
$temp = new SplFileObject( $tempFileName,'w+');
$temp->flock( LOCK_EX );
// Write the temp file without the lines
foreach( $file as $key => $line )
{
if( in_array( $key + 1, $linesToDelete ) === false )
{
$temp->fwrite( $line );
}
}
// File Rename
$file->flock( LOCK_UN );
$temp->flock( LOCK_UN );
unset( $file, $temp ); // Kill the SPL objects relasing further locks
unlink( $fileName );
rename( $tempFileName, $fileName );
可能由于文件大而占用太多空间。 当您执行file('test.txt')
,它将整个文件读入一个数组。 相反,您可以尝试使用Generators
。
GeneratorsExample.php
<?php
class GeneratorsExample {
function file_lines($filename) {
$file = fopen($filename, 'r');
while (($line = fgets($file)) !== false) {
yield $line;
}
fclose($file);
}
function copyFile($srcFile, $destFile) {
foreach ($this->file_lines($srcFile) as $line) {
if(!strstr($line, ".com")) {
$f = fopen($destFile, "a");
fwrite($f, $line);
fclose($f);
}
}
}
}
CallingFile.php
<?php
include('GeneratorsExample.php');
$ob = new GeneratorsExample();
$ob->copyFile('file1.txt', 'file2.txt')
虽然您可以使用数十行PHP代码,但可以使用一行shell代码。
$ grep Bar.com stuff.txt > stuff2.txt
或作为PHP
system ("grep Bar.com stuff.txt > stuff2.txt");
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.