多執行緒多批量插入大資料
阿新 • • 發佈:2019-01-02
package com.test.wyl; import java.util.ArrayList; import java.util.List; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; public class test { public static void exec(List<String> list) throws InterruptedException{ intcount = 300; //一個執行緒處理300條資料 int listSize = list.size(); //資料集合大小 int runSize = (listSize/count)+1; //開啟的執行緒數 List<String> newlist = null; //存放每個執行緒的執行資料 ExecutorService executor = Executors.newFixedThreadPool(runSize); //建立一個執行緒池,數量和開啟執行緒的數量一樣 //建立兩個個計數器 CountDownLatch begin = newCountDownLatch(1); CountDownLatch end = new CountDownLatch(runSize); //迴圈建立執行緒 for (int i = 0; i < runSize ; i++) { //計算每個執行緒執行的資料 if((i+1)==runSize){ int startIndex = (i*count); int endIndex = list.size(); newlist= list.subList(startIndex, endIndex); }else{ int startIndex = (i*count); int endIndex = (i+1)*count; newlist= list.subList(startIndex, endIndex); } //執行緒類 MyThread mythead = new MyThread(newlist,begin,end); //這裡執行執行緒的方式是呼叫執行緒池裡的executor.execute(mythead)方法。 executor.execute(mythead); } begin.countDown(); end.await(); //執行完關閉執行緒池 executor.shutdown(); } //測試 public static void main(String[] args) { List<String> list = new ArrayList<String>(); //資料越大執行緒越多 for (int i = 0; i < 3000000; i++) { list.add("hello"+i); } try { exec(list); } catch (InterruptedException e) { e.printStackTrace(); } } }
package com.test.wyl; import java.util.List; import java.util.concurrent.CountDownLatch; public class MyThread implements Runnable { private List<String> list; private CountDownLatch begin; private CountDownLatch end; //建立個建構函式初始化 list,和其他用到的引數 public MyThread(List<String> list, CountDownLatch begin, CountDownLatch end) { this.list = list; this.begin = begin; this.end = end; } @Override public void run() { try { for (int i = 0; i < list.size(); i++) { //這裡還要說一下,,由於在實質專案中,當處理的資料存在等待超時和出錯會使執行緒一直處於等待狀態 //這裡只是處理簡單的, //分批 批量插入 } //執行完讓執行緒直接進入等待 begin.await(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } finally { //這裡要主要了,當一個執行緒執行完 了計數要減一不然這個執行緒會被一直掛起 // ,end.countDown(),這個方法就是直接把計數器減一的 end.countDown(); } } }