我目前正在开发一个Java项目,我需要准备一个大的(对我来说)mysql数据库。我必须使用Jsoup进行网页抓取并将结果存储到我的数据库中。据我估计,我将插入大约1,500,000到2,000,000条记录。在我的第一次试验中,我只是使用一个循环来插入这些记录,我需要一周的时间来插入大约1/3的所需记录,我认为这太慢了。是否有可能使这个过程成为多线程的,这样我就可以将我的记录分成3组,比如每组500,000条记录,然后将它们插入一个数据库(具体是一个表)?
答案 0 :(得分:5)
多线程不会对您有所帮助。您只需将争用瓶颈从应用服务器移至数据库。
相反,尝试使用批量插入,它们通常会使这种事情的速度提高几个数量级。请参阅"3.4 Making Batch Updates" in the JDBC tutorial。
编辑:正如@Jon评论的那样,您需要将网页的提取与插入数据库中的网页分离,否则整个过程将以最慢的操作速度进行。您可以有多个线程获取网页,这会将数据添加到队列数据结构中,然后让一个线程使用批量插入将队列排入数据库。
答案 1 :(得分:1)
确保两个(或更多)线程不会同时使用相同的连接,使用连接池解析该连接。想到c3po和apache dbcp ......
答案 2 :(得分:1)
您可以将您的记录集分成批量并执行此操作,但也许您应该考虑其他因素。
您是否正在为每个INSERT进行网络往返?如果是,延迟可能是真正的敌人。尝试对这些请求进行批处理以减少网络流量。
您是否开启了交易?如果是,则回滚日志的大小可能是问题。
我建议分析应用服务器和数据库服务器以查看花费的时间。你可以浪费大量的时间来猜测根本原因。
答案 3 :(得分:1)
如果这些记录使用不同的主键值,则可以在不同的线程中插入这些记录。
您还应该查看我认为对您的案例有用的Spring Batch。
答案 4 :(得分:0)
我认为多线程approch对您的问题很有用,但您必须使用 connection pool
,例如C3P0
或Tomca 7 Connetcion pool
才能获得更高的效果。
另一个解决方案是使用批处理操作提供程序,例如Spring-batch
,也存在用于批处理操作的其他实用程序。
另一种解决方案是使用带有PL/SQl Procedure
参数的structure
。