多线程往Oracle数据库里插入数据的优化

该博客探讨了如何通过多线程提高Apache日志分析任务的效率,特别是优化了从日志文件中读取数据并批量插入Oracle数据库的过程。通过调整线程数和每个线程处理的日志数量,实现了在27分钟内插入100万条数据。经过网络优化后,速度提升至7分钟完成100万条数据的入库。
摘要由CSDN通过智能技术生成
昨 天做了一个东西,要实现解析txt文件,然后入库的功能。开始试验了一下单线程插入,速度实在太慢了,半个小时才插入了2W多条数据,后来改用Java的 线程池启用了30个线程,并发的执行,插入100W条数据用了一个多小时。后来又对业务层的事务做了一些调整,每1000条insert之后才提交一次, 一共开了20个线程,最后100W条数据入库一共用了14分钟不到,平均一分钟7.1W条左右。 代码如下:
  1. /**
  2. * 分析Apache日志的定时任务.每天运行数次.
  3. *
  4. * @author <a href="mailto:HL_Qu@hotmail.com">Along</a>
  5. *
  6. * @version $Revision$
  7. *
  8. * @since 2009-2-9
  9. */
  10. public class ApacheLogAnalysisTask {
  11.         /**
  12.          * Logger for this class
  13.          */
  14.         private static final Log logger = LogFactory.getLog(ApacheLogAnalysisTask.class);
  15.        
  16.         //总线程数
  17.         private static final int THREAD_COUNT = 20;
  18.        
  19.         //每个线程插入的日志数
  20.         private static final long LOG_COUNT_PER_THREAD = 1000;
  21.        
  22.         //日志文件的位置
  23.         private static final String LOG_FILE = Property.LOG_FILE_PATH + "formatLog.txt";
  24.        
  25.         private IObjectActionDetailService objectActionDetailService;
  26.        

  27.         public void setObjectActionDetailService(IObjectActionDetailService objectActionDetailService) {
  28.                 this.objectActionDetailService = objectActionDetailService;
  29.         }

  30.         public void execute() {
  31.                 this.multiAnalysisLog();
  32.         }
  33.        
  34.         private void multiAnalysisLog() {
  35.                 ExecutorService exePool = Executors.newFixedThreadPool(THREAD_COUNT);
  36.                
  37.                 FileReader fr = null;
  38.                 BufferedReader br = null;
  39.                 long beginLine = 1;
  40.                 long endLine = 0;
  41.                 String logFileBack = Property.LOG_FILE_PATH + "/formatLog_" + DateUtil.getSystemCurrentDate() + "_" + System.currentTimeMillis() + ".txt";
  42.                
  43.                 try {
  44.                         //文件拷贝出来一个新的,并将原先的删除.
  45.                         FileUtil.copyfile(LOG_FILE, logFileBack, true);
  46.                         FileUtil.deleteFile(LOG_FILE);
  47.                         System.out.println(logFileBack);
  48.                        
  49.                         fr = new FileReader(logFileBack);
  50.                         br = new BufferedReader(fr);
  51.                        
  52.                         while ((br.readLine()) != null){
  53.                                 endLine++;
  54.                                
  55.                                 //每个线程分配固定的行数
  56.                                 if((endLine - beginLine + 1) == LOG_COUNT_PER_THREAD) {
  57.                                         exePool.execute(new AnalysisLogTask(logFileBack, beginLine, endLine));
  58.                                         beginLine = endLine + 1;
  59.                                 }
  60.                         }
  61.                        
  62.                         //最后一个线程
  63.                         if (endLine > beginLine) {
  64.                                 exePool.execute(new AnalysisLogTask(logFileBack, beginLine, endLine));
  65.                         }

  66.                 } catch (FileNotFoundException e) {
  67.                         e.printStackTrace();
  68.                 } catch (IOException e) {
  69.                         e.printStackTrace();
  70.                 } finally {
  71.                         if (br != null) {
  72.                                 try {
  73.                                         br.close();
  74.                                         br = null;
  75.                                 } catch (IOException e) {
  76.                                         if (logger.isErrorEnabled()) {
  77.                                                 logger.error("run()", e);
  78.                                         }

  79.                                         e.printStackTrace();
  80.                                 }
  81.                         }
  82.                        
  83.                         if (fr != null) {
  84.                                 try {
  85.                                         fr.close();
  86.                                         fr = null;
  87.                                 } catch (IOException e) {
  88.                                         if (logger.isErrorEnabled()) {
  89.                                                 logger.error("run()", e);
  90.                                         }

  91.                                         e.pr
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值