有很多解决方案,但这里的特殊性是我需要能够在一条直线内分裂,切割应该发生在模式之前。例如:
填充:
<?xml 1><blabla1>
<blabla><blabla2><blabla>
<blabla><blabla>
<blabla><blabla3><blabla><blabla>
<blabla><blabla><blabla><?xml 4>
<blabla>
<blabla><blabla><blabla>
<blabla><?xml 2><blabla><blabla>
应该变成模式<?xml
出口1:
<?xml 1><blabla1>
<blabla><blabla2><blabla>
<blabla><blabla>
<blabla><blabla3><blabla><blabla>
<blabla><blabla><blabla>
出口2:
<?xml 4>
<blabla>
<blabla><blabla><blabla>
<blabla>
出口3:
<?xml 2><blabla><blabla>
实际上,验证答案here中的perl
脚本对于我的小例子来说很好。但它会为我更大(约6GB)的实际文件生成一个错误。错误是:
panic: sv_setpvn called with negative strlen at /home/.../split.pl line 7, <> chunk 1.
我没有发表评论的权限,这就是我开始发表新文章的原因。
最后,一个Python
的解决方案会更受欢迎,因为我对它有更好的理解。
Perl可以逐行解析大型文件,而不是将整个文件拖入内存。 下面是一个简短的脚本(带说明):
perl -n
:-n标志将逐行循环覆盖您的文件(将内容设置为$)-E
:执行以下文本(Perl默认需要一个文件名)if (/(.*)(<\?xml.*) )
如果行匹配<?xml
请将该行(使用regex匹配)拆分为$1和$2。print $fh $1 if $1
将行首打印到旧文件。open $fh, ">output.". ++$i;
创建用于写入的新文件句柄。print $fh $2
将该行的其余部分打印到新文件。} else { print $fn $_ }
如果行不匹配<?xml
只需将其打印到当前文件句柄。注意:这个脚本假设您的输入文件以
<?xml
开头。在不将所有内容读入RAM的情况下执行拆分:
警告:如果您的模式跨越多行(即包含“\n”),则此操作不起作用。如果是这样,请考虑mmap solution。
对于这种大小的文件,可能需要使用^{} 模块,这样就不必自己处理文件的分块。从那里的文件来看:
下面是一个简单的示例,它向您展示了如何在文件中找到
<?xml #>
的每个匹配项。你可以一边写,一边写,但我还没写。相关问题 更多 >
编程相关推荐