Java 在30GB XML数据集上搜索正则表达式模式。利用16gb内存
我目前有一个JavaSAX解析器,它从一个30GB的XML文件中提取一些信息 目前是:Java 在30GB XML数据集上搜索正则表达式模式。利用16gb内存,java,xml,Java,Xml,我目前有一个JavaSAX解析器,它从一个30GB的XML文件中提取一些信息 目前是: 读取每个XML节点 将其存储到字符串对象中 在字符串上运行一些正则表达式 将结果存储到数据库中 为了几百万个元素。我在一台有16GB内存的计算机上运行这个程序,但是内存没有被充分利用 有没有一种简单的方法可以从输入文件中动态“缓冲”大约10gb的数据 我怀疑我可以手动使用“生产者”“消费者”多线程版本(一边加载对象,一边使用对象,另一边丢弃对象),但该死的是,XML现在已经过时了,没有有效的库来处理它们吗
- 读取每个XML节点
- 将其存储到字符串对象中
- 在字符串上运行一些正则表达式
- 将结果存储到数据库中
我怀疑我可以手动使用“生产者”“消费者”多线程版本(一边加载对象,一边使用对象,另一边丢弃对象),但该死的是,XML现在已经过时了,没有有效的库来处理它们吗?没有Java经验,抱歉,但也许你应该更改解析器?SAX应该按顺序工作,并且不需要缓冲大部分文件…我真的不明白您想用这么多XML做什么,但我得到的印象是
- 对存储的数据使用XML是错误的
- 您的缓冲远远超出了您应该做的(这样做将放弃SAX解析的所有优势)
除此之外,XML并不是古老的,并没有被大量和积极地使用。你认为所有这些互动网站都在使用什么作为互动元素 我建议首先将您的海量XML文件导入到本地XML数据库中(例如,如果您正在寻找开源的东西,我从来没有测试过),然后执行迭代分页查询,一次处理一小块数据。SAX本质上是“事件驱动的”,因此,您应该在元素之间保持的唯一状态是与该元素相关的状态,而不是整个文档。你还保持什么样的状态,为什么?当每个“完整”节点(或一组节点)出现时,您应该丢弃它们。您是否因为对数据库的多个小提交而减慢了速度?听起来您几乎一直在从程序中向db写入数据,确保不经常提交数据可以提高性能。可能还需要准备语句和其他标准批量处理技巧
除了这个早期的评论,我们需要更多的信息-您是否手头有一个分析器,可以找出使事情运行缓慢的原因您可能想尝试代替SAX,我听说它更适合这种类型的事情(我自己没有使用过)。首先,尝试找出是什么让您慢下来
- 从内存解析时,解析器的速度要快多少李>
- 使用大尺寸的
是否有帮助BufferedInputStream
拆分XML文件容易吗?一般来说,在任何类型的30 GiB数据中进行随机扫描都需要一些时间,因为您必须首先从硬盘加载数据,因此您总是受到这种速度的限制。您可以将负载分配到多台机器上吗?也许可以使用类似的方法?您可以使用Jibx库,并将XML“节点”绑定到表示它们的对象上。您甚至可以重载ArrayList,然后在添加x个对象时,一次执行所有正则表达式(可能使用对象上执行此逻辑的方法),然后将它们保存到数据库中,然后再允许“add”方法再次完成 Jibx托管在SourceForge上: 详细说明:您可以将XML绑定为这些专用字符串持有者的“集合”。因为您将其定义为集合,所以必须选择要使用的集合类型。然后可以指定自己的ArrayList实现 按如下方式重写add方法(忘记返回类型,例如假定为void): 要在arraylist中存储多少对象,直到将其刷新到数据库。flushObjects();只是执行此逻辑的方法。该方法将阻止从XML文件添加对象,直到该过程完成。不过,这没关系,无论如何,数据库的开销可能比文件读取和解析要大得多
- StAX(有多种实现;是最快的实现之一)
- 使用自己的
- 使用您自己的特别设置,例如使用正则表达式
如果XML中的数据是顺序独立的,您可以多线程处理该进程以拆分文件,还是从文件中的不同位置开始运行多个进程?如果不受I/O限制,这将有助于加快速度。我会用Perl来完成。就我的0.02美元。你能澄清一下“动态缓冲区”是什么意思吗?应该缓冲什么?我
public void add(Object o) {
super.add(o);
if(size() > YOUR_DEFINED_THRESHOLD) {
flushObjects();
}
}
YOUR_DEFINED_THRESHOLD