Java精简返回给前端的结果集


需求:

前端页面需要展示三级菜单,后端返回结果集。问题在于,JavaBean中的属性值比实际需要的数量多,为了节省后端传递给前端的流量,将不需要的属性值设为null,这样转换为Json字符串的长度会小很多。

难点在于如何将id和parentid设置为null

数据结构要求如下:

 1 [
 2   {
 3     name:"一级菜单"
 4       menus:[ 
 5          {
 6           name:"二级菜单"
 7           menus:[
 8              {
 9                 name:"三级菜单"
10              },
11              .......
12           ]
13        },
14        .......
15       ]
16   },
17   .......
18 ]
接口文档

数据库中数据表:

 1 CREATE TABLE `tb_ad` (
 2   `id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'ID',
 3   `name` varchar(50) DEFAULT NULL COMMENT '广告名称',
 4   `position` varchar(50) DEFAULT NULL COMMENT '广告位置',
 5   `start_time` datetime DEFAULT NULL COMMENT '开始时间',
 6   `end_time` datetime DEFAULT NULL COMMENT '到期时间',
 7   `status` char(1) DEFAULT NULL COMMENT '状态',
 8   `image` varchar(100) DEFAULT NULL COMMENT '图片地址',
 9   `url` varchar(100) DEFAULT NULL COMMENT 'URL',
10   `remarks` varchar(1000) DEFAULT NULL COMMENT '备注',
11   PRIMARY KEY (`id`)
12 )
数据表结构

对应的JavaBean如下:

 1 @Table(name="tb_category")
 2 public class Category implements Serializable{
 3 
 4     @Id
 5     private Integer id;//分类ID
 6 
 7     private String name;//分类名称
 8 
 9     private Integer goodsNum;//商品数量
10 
11     private String isShow;//是否显示
12 
13     private String isMenu;//是否导航
14 
15     private Integer seq;//排序
16 
17     private Integer parentId;//上级ID
18 
19     private Integer templateId;//模板ID
20     private List<Category> menus;
21         //省略get/set
22 
23 }
JavaBean

方式一,在双层嵌套循环的过程中,在适当位置将id和parentid赋值为null。

优点,代码编写简单,测试容易。缺点,对于非包装类型无能为力,逻辑有点绕。

 1     public List<Category> findCategoryTree() {
 2         //1.查找所有需要显示的category
 3         Example example = new Example(Category.class);
 4         Example.Criteria criteria = example.createCriteria();
 5         criteria.andEqualTo("isShow","1");
 6         example.setOrderByClause("seq");//排序
 7         List<Category> categories = categoryMapper.selectByExample(example);
 8         ArrayList<Category> parentList = new ArrayList<>();
 9         //2.通过递归的方式,给menus赋值
10         for (Category category : categories) {
11             //一级category
12             if(Objects.nonNull(category.getParentId())&&category.getParentId()==0){
13                 //清除一级目录的parentId
14                 category.setParentId(null);
15                 parentList.add(category);
16             }
17             findChildren(categories,category);
18             category.setGoodsNum(null);
19             category.setIsMenu(null);
20             category.setIsShow(null);
21             category.setSeq(null);
22             category.setTemplateId(null);
23         }
24         return parentList;
25     }
26 
27     private void findChildren(List<Category> categories, Category category){
28         List<Category> list=new ArrayList<>();
29         for (Category category1 : categories) {
30             if(category.getId().equals(category1.getParentId())){
31                 //到此说明已经找到它的father,那么parentId已经没有用了
32                 category1.setParentId(null);
33                 list.add(category1);
34             }
35         }
36         //到此说明已经找到它所有的children,那么id已经没有用了
37         category.setId(null);
38         if(list.size()>0){
39             category.setMenus(list);
40         }
41     }
方式一

方式二,讲树状的结果集转为json字符串,利用正则表达式替换掉不需要的属性,然后再将字符串转为Object。

优点,对于非包装类的属性也适用,代码重复利用性高。缺点,会生成多个字符串常量,占用内存稍高,正则表达式写起来麻烦,不容易测试。

 1     public Object findCategoryTree() {
 2         //1.查找所有需要显示的category
 3         Example example = new Example(Category.class);
 4         Example.Criteria criteria = example.createCriteria();
 5         criteria.andEqualTo("isShow","1");
 6         example.setOrderByClause("seq");//排序
 7         List<Category> categories = categoryMapper.selectByExample(example);
 8         ArrayList<Category> parentList = new ArrayList<>();
 9         //2.通过递归的方式,给menus赋值
10         for (Category category : categories) {
11             //一级category
12             if(Objects.nonNull(category.getParentId())&&category.getParentId()==0){
13                 //清除一级目录的parentId
14                 //category.setParentId(null);
15                 parentList.add(category);
16             }
17             findChildren(categories,category);
18             category.setGoodsNum(null);
19             category.setIsMenu(null);
20             category.setIsShow(null);
21             category.setSeq(null);
22             category.setTemplateId(null);
23         }
24        //3.通过自定义方法将"id","parentId"属性移除
25         ArrayList<String> attributes = new ArrayList<>();
26         attributes.add("id");
27         attributes.add("parentId");
28         return AttributeUtils.removeAttribute(parentList,attributes);
29     }
30 
31     private void findChildren(List<Category> categories, Category category){
32         List<Category> list=new ArrayList<>();
33         for (Category category1 : categories) {
34             if(category.getId().equals(category1.getParentId())){
35                 //到此说明已经找到它的father,那么parentId已经没有用了
36                 //category1.setParentId(null);
37                 list.add(category1);
38             }
39         }
40         //到此说明已经找到它所有的children,那么id已经没有用了
41         //category.setId(null);
42         if(list.size()>0){
43             category.setMenus(list);
44         }
45     }
方式二

自定义工具类

 1 public class AttributeUtils {
 2     public static <T> Object removeAttribute(List<T> list, List<String> attributeNames) {
 3         //1.将list转为json字符串
 4         String jsonString = JSONObject.toJSONString(list);
 5         //2.删除掉json字符串中相关属性及属性值
 6         for (String attributeName : attributeNames) {
 7             //元素在开头
 8             String regex1 = "[^,]\""+attributeName+"\":*[^}]*?,";
 9             Pattern p1 = Pattern.compile(regex1);
10             Matcher m1 = p1.matcher(jsonString);
11             jsonString = m1.replaceAll("{");
12             //元素在尾部
13            String regex2 = ",\""+attributeName+"\":*[^{]*?}";
14             Pattern p2 = Pattern.compile(regex2);
15             Matcher m2 = p2.matcher(jsonString);
16             jsonString=m2.replaceAll("}");
17             //元素在中间
18             String regex3 = ",\""+attributeName+"\":*[^{]*?,";
19             Pattern p3 = Pattern.compile(regex3);
20             Matcher m3 = p3.matcher(jsonString);
21             jsonString=m3.replaceAll("");
22         }
23         Object parse = JSONObject.parse(jsonString);
24         return parse;
25     }
26 }
工具类

 


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM