我有一个像some.txt
这样的文件,内容为:
#start-first
Line 1
Line 2
Line 3
#end-first
#start-second
Line 1
Line 2
Line 3
Line 4
#end-second
#start-n
Line 1
Line 2
Line 3
Line 4
...
...
#end-n
我想从#start-second
到#end-second
或从#start-n
到#end-n
删除文件中的内容,实际上#start-second
是启动标记 for 第二个文本块文件,#end-second
是结束标记 第二个文本块文件。
如何将特定起始块中的内容删除到同一个结束块?
答案 0 :(得分:2)
如果这些文件非常大,那么有一个相当轻量级的解决方案:
$file = file_get_contents("example.txt");
// Find the start "#start-$block", "#end-$block" and the length between them:
$start = strpos($file, "#start-$block");
$end = strpos($file, "#end-$block");
$length = $end-$start+strlen("#end-$block");
$file = substr_replace($file, '', $start, length);
file_put_contents("example.txt", $file);
我的原始答案始于正则表达式:
$block = 4;
// Open the file
$file = openfile("example.txt");
// replace #start-$block, #end-$block, and everything inbetween with ''
$file = preg_replace("/#start\-".$block."(?:.*?)#end\-".$block."/s", '', $file);
// Save the changes
file_put_contents("example.txt", $file);
但是,正则表达式很昂贵,但有时更容易理解。
答案 1 :(得分:0)
这是我的解决方案:
逐行执行它有点困难,但它确实可以让您更好地管理大型文件的内存,因为您不能一次性打开整个文件。此外,您可以通过这种方式更轻松地替换多个块。
var obj = {
aray1:[1,2],
aray2:["a","b"],
aray3:["ab","abab"]
};
var result = "";
for(key in obj){
result += ","+obj[key].join(",")
}
console.log(result.substring(1));
输出
$file = 'test.txt';
//open file to read from
$f = fopen(__DIR__.DIRECTORY_SEPARATOR.$file,'r');
//open file to write to
$w = fopen(__DIR__.DIRECTORY_SEPARATOR.'out-'.$file,'w');
$state = 'start'; //start, middle, end
//start - write while looking for a start tag ( set to middle )
//middle - skip while looking for end tag ( set to end )
//end - skip while empty ( set to start when not )
//Tags
$start = ['#start-second'];
$end = ['#end-second'];
//read each line from the file
while( $line = fgets($f)){
if( $state == 'end' && !empty(trim($line))){
//set to start on first non empty line after tag
$state = 'start';
}
if( $state == 'start' ){
if(in_array(trim($line),$start)){
$state = 'middle';
}else{
fwrite($w, $line);
}
}else if( $state == 'middle' ){
if(in_array(trim($line),$end)){
$state = 'end';
}
}
}
//close both files
fclose($f);
fclose($w);
//delete the input file
//unlink(__DIR__.DIRECTORY_SEPARATOR.$file);
//for debugging only
echo "<pre>";
echo file_get_contents(__DIR__.DIRECTORY_SEPARATOR.'out-'.$file)
这也会接受一系列标记,因此您可以逐个删除多个块。
出于安全原因,大多数PHP沙箱(或一般的代码沙箱)都会阻止您使用这些功能。也就是说,我们可以在某种程度上#start-first
Line 1
Line 2
Line 3
#end-first
#start-n
Line 1
Line 2
Line 3
Line 4
...
...
#end-n
代码的主体,解析位。这就是我在这里所做的。
http://sandbox.onlinephpfunctions.com/code/0a746fb79041d30fcbddd5bcb00237fcdd8eea2f
这样你可以尝试一些不同的标签,看看它是如何工作的。为了获得额外的功劳,你可以将它变成一个接受文件路径和一系列open和start标签的函数。
emulate