在实际业务中,分类表中或菜单表中 数据得关系会有一种树形关系,在表的设计中一般会在表中添加一个parentId字段,

在查询这类数据一般有两种方式

一种是采用业务逻辑将其组装成树状结构

另外一种是通过sql语句及mybatis将其组装成树状结构

使用流将分类关系组成树状结构

/**
* 以树形结构返回
*
* @return
*/
    @Override
    public List<UmsMenuNode> treeList() {
        //所有的菜单
        List<UmsMenu> menuList = umsMenuMapper.selectByExample(new UmsMenuExample());
        //将菜单组装成节点
        List<UmsMenuNode> nodes = menuList.stream()
                //找出所有父节点
                .filter(menu -> menu.getParentId().equals(0L))
                .map(menu -> covertMenuNode(menu, menuList))
                .collect(Collectors.toList());
        return nodes;
    }
/**
 * 将UmsMenu 转化为UmsMenuNode 并设置children属性 递归完成
 *
 * @param menu
 * @param menuList
 * @return
 */
private UmsMenuNode covertMenuNode(UmsMenu menu, List<UmsMenu> menuList) {
    UmsMenuNode node = new UmsMenuNode();
    BeanUtil.copyProperties(menu, node);
    List<UmsMenuNode> children = menuList.stream()
            .filter(subMenu -> subMenu.getParentId().equals(menu.getId()))
            .map(subMenu -> covertMenuNode(subMenu, menuList))
            .collect(Collectors.toList());
    node.setChildren(children);
    return node;
}

sql完成树状分类 只有两级

商品分类实体类

public class PmsProductCategory implements Serializable {
    private Long id;

    @ApiModelProperty(value = "上机分类的编号:0表示一级分类")
    private Long parentId;

    private String name;

    @ApiModelProperty(value = "分类级别:0->1级;1->2级")
    private Integer level;

    private Integer productCount;

    private String productUnit;

    @ApiModelProperty(value = "是否显示在导航栏:0->不显示;1->显示")
    private Integer navStatus;

    @ApiModelProperty(value = "显示状态:0->不显示;1->显示")
    private Integer showStatus;

    private Integer sort;

    @ApiModelProperty(value = "图标")
    private String icon;

    private String keywords;

    @ApiModelProperty(value = "描述")
    private String description;

商品分类返回实体类

/**
 * @author by cyf
 * @date 2020/6/15.
 */
@Getter
@Setter
public class PmsProductCategoryWithChildren extends PmsProductCategory {
    private List<PmsProductCategory> children;
}

sql语句

<resultMap id="listWithChildren" type="com.cyf.malldemo.dto.PmsProductCategoryWithChildren"
              extends="com.cyf.malldemo.mbg.mapper.PmsProductCategoryMapper.BaseResultMap">
       <collection property="children" resultMap="com.cyf.malldemo.mbg.mapper.PmsProductCategoryMapper.BaseResultMap"
                   columnPrefix="child_"></collection>
   </resultMap>

    <select id="listWithChildren" resultMap="listWithChildren">
        select
          c1.id,
          c1.name,
          c2.id child_id,
          c2.name child_name
        from pms_product_category c1
          left join pms_product_category c2
          on c1.id = c2.parent_id
        where c1.parent_id = 0
    </select>
</mapper>

mysql中查询得到数据, ``mybatis根据resultMap`封装进对象

mysql> use mall;
Database changed
mysql>  select
          c1.id,
          c1.name,
          c2.id child_id,
          c2.name child_name
        from pms_product_category c1
          left join pms_product_category c2
          on c1.id = c2.parent_id
        where c1.parent_id = 0;
+----+----------+----------+--------------+
| id | name     | child_id | child_name   |
+----+----------+----------+--------------+
|  1 | 服装     |        7 | 外套         |
|  1 | 服装     |        8 | T恤          |
|  1 | 服装     |        9 | 休闲裤       |
|  1 | 服装     |       10 | 牛仔裤       |
|  1 | 服装     |       11 | 衬衫         |
|  2 | 手机数码 |       19 | 手机通讯     |
|  1 | 服装     |       29 | 男鞋         |
|  2 | 手机数码 |       30 | 手机配件     |
|  2 | 手机数码 |       31 | 摄影摄像     |
|  2 | 手机数码 |       32 | 影音娱乐     |
|  2 | 手机数码 |       33 | 数码配件     |
|  2 | 手机数码 |       34 | 智能设备     |
|  3 | 家用电器 |       35 | 电视         |
|  3 | 家用电器 |       36 | 空调         |
|  3 | 家用电器 |       37 | 洗衣机       |
|  3 | 家用电器 |       38 | 冰箱         |
|  3 | 家用电器 |       39 | 厨卫大电     |
|  3 | 家用电器 |       40 | 厨房小电     |
|  3 | 家用电器 |       41 | 生活电器     |
|  3 | 家用电器 |       42 | 个护健康     |
|  4 | 家具家装 |       43 | 厨房卫浴     |
|  4 | 家具家装 |       44 | 灯饰照明     |
|  4 | 家具家装 |       45 | 五金工具     |
|  4 | 家具家装 |       46 | 卧室家具     |
|  4 | 家具家装 |       47 | 客厅家具     |
|  5 | 汽车用品 |       48 | 全新整车     |
|  5 | 汽车用品 |       49 | 车载电器     |
|  5 | 汽车用品 |       50 | 维修保养     |
|  5 | 汽车用品 |       51 | 汽车装饰     |
|  1 | 服装     |       54 | 改手表大哥大 |
+----+----------+----------+--------------+
30 rows in set