for循环中进行联网请求数据、for循环中进行异步数据操作,数据排序错乱问题解决;
for循环中进行联网请求数据,由于网络请求是异步的,第一个网络请求还没有回调,第二次第三次以及后续的网络请求又已经发出去了,有可能后续的网络请求会先回调;这时我们接收到的数据的排序就会错乱;怎么才能让数据和for循环进行异步操作之前的顺序一样呢;
1、网络请求使用同步请求,串型请求,等第一个网络请求回调后再去请求第二个;
2、递归迭代,异步的网络请求,在当前请求完成后再去递归请求下一个;
但是这两种方式都不是并发的,如果数据特别的多一个一个的去请求就会特别的耗时,我们用for循环异步去请求就会同时相应,速度回很快;
3、重点要说的:for循环中进行联网请求数据,解决数据排序错乱问题。
第一:记录下来这个for循环 原集合的索引位置(集合中的对象添加一个indexes的字段),用来后续的排序;
第二:异步请求后数据会错乱,这时我们根据indexes的大小进行排序;
代码如下:仅留下解决数据排序错乱问题的代码;
//原数据中缺少一个字段,需要异步请求网络拿到这个字段,全部的异步请求回调后再对原数据进行排序;
private void initNewCars(List<CarInfo> datas) {
for (int ii = 0; ii < datas.size(); ii++) {
datas.get(ii).indexes = ii; //保存当前车辆的索引位置,等集合遍历完成后进行排序
}
AtomicInteger CarSize = new AtomicInteger(); //等所有的集合都联网循环完毕后再去设置数据
List<CarInfo> Cars = new ArrayList<>(); //遍历后对数据进行操作生成新的集合
for (int i = 0; i < datas.size(); i++) {
int finalI = i;
clwOwnerApi.getAuthVehicleStatus(datas.get(finalI).getVin_code()) //异步网络请求
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Consumer<ResultClw<AuthVehicleStatusBean>>() {
@Override
public void accept(ResultClw<AuthVehicleStatusBean> result) throws Exception {
CarSize.getAndIncrement();
if ("SUCCEED".equals(result.status) && result.data != null) {
if (!"0".equals(result.data.getAuditResult()) && result.data.getVehicleStatus()){
}else {
CarInfo carInfo = datas.get(finalI);
carInfo.isClw = result.data.getVehicleStatus();
Cars.add(carInfo); //数据错乱,需要排序!
}
} else {
UIHelper.showToast(result.errorMessage);
}
if (CarSize.get() >= datas.size()){ //等所有的集合都循环完成了再去设置数据
L.cc("列表排序前:"+GsonUtils.toJson(Cars));
//根据保存的索引位置进行排序
Collections.sort(Cars, new Comparator<CarInfo>() {
@Override
public int compare(CarInfo o1, CarInfo o2) {
return o1.indexes - o2.indexes;
}
});
L.cc("列表排序后:"+GsonUtils.toJson(Cars));
}
}
}, throwable -> {
L.e(throwable,throwable.getMessage());
CarSize.getAndIncrement();
UIHelper.showToast("响应服务器失败,请检查网络连接");
});
}
}
对集合的排序参考:https://blog.csdn.net/veryisjava/article/details/51675036
CarInfo对象:
public class CarInfo {
private String id;
private String series;
private String owner_name;
private String vin_code;
private String is_default;
private String uuid;
private String deliver_date;
private String vin_name;
private String card_id;
private String auth_date;
private String mobile;
public boolean isClw;
public int indexes; //记录当前的位置,用来排序
}
**大致思路:
1、判断集合是否循环完成:异步操作,等所有的异步都完成了再去设置数据;使用AtomicInteger记录数据是否全部遍历完成了;
2、数据错乱问题:先给原数据添加索引位置字段,记录原数据的顺序;异步操作集合后数据错乱,在根据数据的索引字段去排序就OK了,这样的数据的顺序还是和原数据的顺序是一致的,并且是并发的异步请求,速度快效率高;
for循环中进行联网请求数据、for循环中进行异步数据操作,数据排序错乱问题解决;的更多相关文章
- Postman中添加真实请求(Chrome Networks中的全部请求,含https)copy as har
Postman中添加真实请求(Chrome Networks中的全部请求,含https) xyxzfj 关注 2018.05.22 19:44* 字数 559 阅读 1176评论 0喜欢 0 Post ...
- 2016/05/13 Thinkphp 3.2.2 ①数据添加 ②收集表单数据入库操作 ③数据修改操作
①数据查询 add() 该方法返回被添加的新记录的主键id值 两种方式实现数据添加 数组方式数据添加 $goods = D(“Goods”); $arr = array(‘goods_name’=&g ...
- Vue中发送ajax请求——axios使用详解
axios 基于 Promise 的 HTTP 请求客户端,可同时在浏览器和 node.js 中使用 功能特性 在浏览器中发送 XMLHttpRequests 请求 在 node.js 中发送 htt ...
- ajax请求返回数据,模板中的数据处理
/*ajax请求返回数据,模板中的数据处理*/ function QueryGameAsset(){ var new_start_time=$('#new_start_time').val();//开 ...
- 联网请求数据:Android篇
这篇文章主要回顾之前的MYangtzeu App教程的联网请求方法和json解析套路,主要目的是实现左侧菜单数据的联网获取. 1.先上请求地址实体类Constants.java package com ...
- 在 Angular6 中使用 HTTP 请求服务端数据
第一步 准备好api接口地址, 例如 https://api.example.com/api/ 第二步 在根组件 app.module.ts 中引入 HttpClientModule 模块. // a ...
- 远程请求json数据,list中显示
public class MainActivity extends Activity { protected static final int WHAT_REQUEST_SUCCESS = 1; pr ...
- HashMap封装的数据用循环快速添加进list中产生的数据集全部相同的问题
一.问题概述 在一次使用SimpleAdapter时,Data需要使用传入一条数据(Image.Text),该数据条使用HashMap封装.在用HashMap封装的数据用循环快速添加进list中产生了 ...
- springMVC中对HTTP请求form data和request payload两种数据发送块的后台接收方式
最近在做项目中发现,前台提交数据时,如果通过form表单提交和ajax发送json时,springMVC后台接收不能都通过@ModelAttribute方式处理,经过一番查找后,ajax发送json请 ...
随机推荐
- 在HTML中导入外部的css
1,标签:<link type="text/css" rel="stylesheet" href="CSS样式文件的绝对地址"> ...
- ML(7)——支持向量机1(构建支持向量机)
支持向量机缩写是SVM(support vaector machine),这里的“机(machine)”是一个算法.在机器学习领域,常把一些算法看做是一个机器,如感知机(也叫感知器).支持向量机本身是 ...
- No MaterialLocalizations found (Flutter)
在显示SimpleDialog时候程序报错 No MaterialLocalizations found 没有找到 MaterialLocalizations 搜索找到原因 runApp 需要先调用 ...
- 获取TypeError:__init __()缺少1个需要的位置参数:'on_delete'当试图添加父表后面的子表
解决办法:https://stackoverflow.com/questions/44026548/getting-typeerror-init-missing-1-required-position ...
- Azkaban介绍+安装部署+实战案例
Azkaban介绍 什么是azkaban?1.工作流的作业调度系统2.通过k.v指令写法描述工作流节点3.可以通过web界面去管理工作流 Azkaban安装部署 2.3.1 准备工作 Azkaban ...
- 集群RedHat6.5+JDK1.8+Hadoop2.7.3+Spark2.1.1+zookeeper3.4.6+kafka2.11+flume1.6环境搭建步骤
1.RHEL 6.5系统安装配置图解教程(rhel-server-6.5) 2.在Linux下安装JDK图文解析 3.RedHat6.5上安装Hadoop集群 4.RedHat6.5安装Spark集群 ...
- max_result_window
PUT http://192.168.1.12:9200/_settings { "index": { "max_result_window": "1 ...
- java线程池ThreadPoolExecutor类使用详解
在<阿里巴巴java开发手册>中指出了线程资源必须通过线程池提供,不允许在应用中自行显示的创建线程,这样一方面是线程的创建更加规范,可以合理控制开辟线程的数量:另一方面线程的细节管理交给线 ...
- CAD求交点函数
public void IntersectWith( Entity entityPointer, Intersect intersectType, Point3dCollection points, ...
- RAMOS_XP制作教程
RAMOS_XP制作教程1.为了防止做系统时出现意外,用Bootice把C盘MBR修改为Grub4dos,这样子系统如果失败,可以进入PE重做. 2.进入PE格式化C盘,格式化的时候勾选启用NTFS压 ...