您的位置:首页 > 其它

关于多线程处理数据并发问题处理

2017-09-05 15:14 323 查看
数据量多时需要要多线程处理,尤其在集群环境下很可能发生资源竞争的情况,此时就需要谨慎的对数据加锁,如果加锁出了问题,也是个麻烦事。

为安全考虑,一般处理这种问题有几个步骤:

为此个业务加开关,如果出现问题,将开关关闭。但是遇到一些紧急问题,开关关闭会影响业务,这时就需要走以下逻辑:

1、数据量多,则数据取出后用线程池分批处理数据。

2、数据量不多,单线程就可以处理;建议建一个线程表专门处理线程锁问题。这里我们建一个asgin_thread的线程表,表中的字段有id,SYNSTATE,VERSION,其中SYNSTATE为同步状态,VERSION为版本号;其中的id是自己定义的,加锁时也只加锁这个表中的某一条数据,不能对业务表进行加锁,将事务放到biz层,这样的话整个biz层的逻辑同在一个事务内,加锁才起作用。此处用乐观锁处理,将asgin_thread的单条数据加锁后,统一业务层的其他逻辑都完成事务提交后锁释放。以下是代码:

while (running) {

      try {

        Thread.sleep(sleepTime);

      } catch (InterruptedException e) {

        log.error("异常:", e);

      }

      List<Bean> tasklist = null;

      try {

        tasklist = asignThreadBiz.update(loadCount);

        log.info("装载已锁定数据");

      } catch (Exception e) {

        log.error("线程出现锁冲突,重新进行取数据....!",e);

        continue;

      } 

      

      if (tasklist != null && !tasklist.isEmpty()) {

        

        WorkThread<List<Bean>> ecThread = createWorkThread();

        ecThread.setTaskList(tasklist);

        threadPool.execute(ecThread);

      }

      // 状态重制

      resetStatus();

    }

处理数据流程:

  asignDao.updateCount();  //线程表单条数据加锁

    List<Bean> retlist = new ArrayList<Bean>();

    

    int retval = BeantDao.setLock(loadcount); //打标记

    if(retval > 0){

      retlist = beantDao.loadLock(); //取数据

    }

乐观锁:

AsginThread asgin = this.load(100000L);
asgin.setSynstate(asgin.getSynstate()+1);
this.saveOrUpdate(asgin);
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: