提示:JVM堆内存配置低.存在内存溢出.
代码:
public List<UserQueryDTO> getResult(UserQuery userQuery) throws Exception {
long start = System.currentTimeMillis();
//返回结果
List<UserQueryDTO> result = new ArrayList<>();
// 通过count查到数据总量
int count = userService.listUserExportCount(userQuery);
int num = 2000;//每次查询的条数
//需要查询的次数
int times = count / num;
if (count % num != 0) {
times = times + 1;
}
//开始查询的行数
int bindex = 0;
//添加任务
List<Callable<List<UserQueryDTO>>> tasks = new ArrayList<Callable<List<UserQueryDTO>>>();
for (int i = 0; i < times; i++) {
Callable<List<UserQueryDTO>> qfe = new ThredQuery(userService, userQuery, bindex, num);
tasks.add(qfe);
bindex = bindex + num;
}
//定义固定长度的线程池 防止线程过多
ExecutorService execservice = Executors.newFixedThreadPool(15);
List<Future<List<UserQueryDTO>>> futures = execservice.invokeAll(tasks);
// 处理线程返回结果
if (CollectionUtils.isNotEmpty(futures)) {
for (Future<List<UserQueryDTO>> future : futures) {
result.addAll(future.get());
}
}
// 关闭线程池
execservice.shutdown();
long end = System.currentTimeMillis();
if (log.isInfoEnabled()) {
log.info("开启多线程查询导出数据耗时:{},共:{}条", (end - start), result.size());
}
return result;
}
public class ThredQuery implements Callable<List<UserQueryDTO>> {
private IUserQueryService userService;//需要通过够早方法把对应的业务service传进来 实际用的时候把类型变为对应的类型
private UserQuery userQuery;//查询条件 根据条件来定义该类的属性
private int bindex;//分页index
private int num;//数量
/**
* 重新构造方法
*
* @param userService
* @param userQuery
* @param bindex
* @param num
*/
public ThredQuery(IUserQueryService userService, UserQuery userQuery, int bindex, int num) {
this.userService = userService;
this.userQuery = userQuery;
this.bindex = bindex;
this.num = num;
}
@Override
public List<UserQueryDTO> call() throws Exception {
//通过service查询得到对应结果
List<UserQueryDTO> list = new ArrayList<>();
userQuery.setStart(bindex);
userQuery.setLimit(num);
list = userService.listUserExport(userQuery);
return list;
}
}