假设有两个对象 A,B 且是 1 对多的关系
class A {
int id;
List<B> bs;
}
class B {
int a_id;
String name;
}
现在需要获取 A 的列表。
先获取 A 的列表,然后遍历通过 a_id 获取对应的 B 的列表,再 set 进 A,这样多次 io 较慢
用 sql join 将全部数据从数据库中取出,在内存中运算筛选封装。
问下大佬们有没有更好的做法?先谢为敬
1
Eugene1024 2018-08-31 17:25:24 +08:00
直接
class C { int a_id; int b_id; String name; } 前端显示 C,a_id 相同的合并,我的理解 |
2
vjnjc 2018-08-31 19:46:16 +08:00 via Android
看你业务,假如不同 aid 对应的 blist 有交集的话,做一个 b 对象的缓存。就是已经读取过的 b 都还存在内存 cache 里,Hashmap ( id,b ) bcache=new Hashmap...
|
3
mmdsun 2018-08-31 20:22:57 +08:00 via Android
mybatis collection 处理一对多配置好就直接查出来了 sql join。大表不方便连表可以用第一种。
|
4
talen666 2018-08-31 22:15:53 +08:00
同意楼上 mybatis collection。
|
5
TommyLemon 2018-08-31 23:52:08 +08:00
JOIN 直接就解决了,只取需要的而不是全部数据,为啥还要在内存中(我的理解是应用层,而不是数据库引擎)筛选?
```sql SELECT A.*, B.* FROM A INNER JOIN B ON A.id = B.a_id WHERE {A 和 B 里面字段的条件} ``` 封装是肯定要在应用层搞定的,遍历 ResultSet 再封装 A,B 即可,A 很可能会有重复,所以最好用 ```java Map<a_id, A> aMap = new LinkedHashMap<>(); ``` 这样的结构,每次 ```java A a = aMap.get(a_id); if (a == null) { a = new A(); aMap.put(a_id, A); } a.setId(a_id); ... List<B> bs = a.getBs(); if (bs == null) { bs = new ArrayList<>(); a.setBs(bs); } B b = new B(); b.setA_id(a_id); ... bs.add(b); ``` 如果你懒得封装,其实可以用 APIJSON 的自动化 API 帮你搞定: 请求 ```javascript { "Moment": {}, "Comment[]": { //把数组里面每项的 Comment 对象提取出来 "Comment": { "momentId@": "Moment/id" // 引用赋值:Comment.momentId = Moment.id } } } ``` 返回: ```javascript { "Moment": { "id": 12, "userId": 70793, "date": "2017-02-08 16:06:11.0", "content": "1111534034", "praiseUserIdList": [ 70793, 93793 ], "pictureList": [ "http://static.oschina.net/uploads/img/201604/22172508_eGDi.jpg" ] }, "Comment[]": [ { "id": 162, "toId": 0, "userId": 93793, "momentId": 12, "date": "2017-03-06 13:03:45.0", "content": "This is a Content...-162" }, { "id": 164, "toId": 0, "userId": 93793, "momentId": 12, "date": "2017-03-06 13:03:45.0", "content": "This is a Content...-164" }, { "id": 172, "toId": 162, "userId": 82001, "momentId": 12, "date": "2017-03-25 20:22:58.0", "content": "OK" } ], "code": 200, "msg": "success" } ``` APIJSON 自动将前端传的 JSON 参数转为 SQL 语句执行并返回结果, 期间自动校验权限、结构、内容,自动防 SQL 注入。 通过自动化 API,前端可以定制任何数据、任何结构! 大部分 HTTP 请求后端再也不用写接口了,更不用写文档了! 前端再也不用和后端沟通接口或文档问题了!再也不会被文档各种错误坑了! 后端再也不用为了兼容旧接口写新版接口和文档了!再也不会被前端随时随地没完没了地烦了! 在线解析 自动生成文档,清晰可读永远最新 自动生成请求代码,支持 Android 和 iOS 自动生成 JavaBean 文件,一键下载 自动管理与测试接口用例,一键共享 自动校验与格式化 JSON,支持高亮和收展 对于前端 不用再向后端催接口、求文档 数据和结构完全定制,要啥有啥 看请求知结果,所求即所得 可一次获取任何数据、任何结构 能去除重复数据,节省流量提高速度 对于后端 提供通用接口,大部分 API 不用再写 自动生成文档,不用再编写和维护 自动校验权限、自动管理版本、自动防 SQL 注入 开放 API 无需划分版本,始终保持兼容 支持增删改查、模糊搜索、正则匹配、远程函数等 后端接口和文档自动化,前端(客户端) 定制返回 JSON 的数据和结构! 创作不易,GitHub 右上角点 Star 支持下吧,谢谢^_^ github.com/TommyLemon/APIJSON |
6
TommyLemon 2018-08-31 23:56:53 +08:00
@TommyLemon 纯手打,有个错误,
Map<a_id, A> aMap = new LinkedHashMap<>(); 要改成 Map<Integer, A> aMap = new LinkedHashMap<>(); |
7
TommyLemon 2018-08-31 23:58:38 +08:00
@TommyLemon INNER JOIN 可实现多表条件组合,如果只是根据 A 取 B,应该改用 LEFT JOIN
|
8
samples OP |