多线程分块读取数据表的设计与实现

一、应用场景

项目场景描述:数据表中共有45万条记录,如果使用单线程读取,需要耗费大约1个多小时的时间,因此考虑使用多线程读取数据表,将其加载到内存中。
项目需求:
  • 多线程读取数据表,要求在1分钟之内将数据加载到内存中;
  • 存储数据的数据结构为Map,要考虑其线程安全;
  • 子线程读取数据完成后,主线程要进行相应的操作,因此设计中要考虑主线程等待子线程完成。

二、设计思路

2.1 分块读取数据表数据设计

数据表中主键为id,使用WHERE和LIMIT,来对数据表进行划块,SQL语句如:SELECT * FROM table_name WHERE id > 'var' LIMIT 10000。如果整个数据表中有45万条数据,则需要开45个线程取做该项任务。

2.2 多线程设计

多线程设计中需要考虑的是主线程等待子线程结束, 使用 java.util.concurrent中的 CountDownLatch,是一个倒数计数器。初始化时先设置一个倒数计数初始值,每调用一次countDown()方法,倒数值减一,他的await()方法会阻塞当前进程,直到倒数至0。使用过程中,要注意线程数要与CountDownLatch中的计数器数量一致。示例代码如下:
import java.util.concurrent.CountDownLatch;  
  
public class MyThread2 extends Thread  
{  
    private CountDownLatch count;  
    public MyThread2(CountDownLatch count, String name)  
    {  
        this.count = count;  
        this.setName(name);  
    }  
  
    @Override  
    public void run()  
    {  
        System.out.println(this.getName() + " staring...");  
        System.out.println(this.getName() + " end...");  
        this.count.countDown();  
    }   
    /** 
     * @param args 
     */  
    public static void main(String[] args)  
    {  
        System.out.println("main thread starting...");  
  
        CountDownLatch count = new CountDownLatch(5);  
  
        for (int i = 1; i <= 5; i++)  
        {  
            MyThread2 my = new MyThread2(count, "Thread " + i);  
            my.start();  
        }  
  
        try  
        {  
            count.await();  
        }  
        catch (InterruptedException e)  
        {  
            e.printStackTrace();  
        }  
  
        System.out.println("main thread end...");  
  
    }  
  
}  
运行结果如下:

main thread starting...
Thread 2 staring...
Thread 2 end...
Thread 4 staring...
Thread 4 end...
Thread 1 staring...
Thread 1 end...
Thread 3 staring...
Thread 3 end...
Thread 5 staring...
Thread 5 end...
main thread end...

本项目中,主线程用来给每个线程分配其对应的分块,实现得方法为,主线程中完成一个子进程的分配则将id加到下一个进程获取数据区块的起始id。。

2.3 线程安全的Map

存储数据时,使用线程安全的Map——ConcurrentHashMap

三、结论

最终,加载数据表中数据如内存,耗时42s。



你可能感兴趣的:(Java,MySQL,算法设计)