import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONUtil;
import com.alibaba.fastjson.JSON;
import org.springframework.stereotype.Component;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Hashtable;
import java.util.List;
import java.util.Map;
/**
* list转换成树形结构
*/
@Component
public class ConvertorUtil<T> {
public static String PRIMARY_FIELD_NAME = "id";
public static String PARENT_FIELD_NAME = "pid";
public static String CHILDREN_LIST = "childrenList";
public static String PID_VALUE = "0";
public static String PRIMARY_FIELD_ENDS_WITH= "Pid";
public static String PARENT_FIELD_ENDS_WITH= "Id";
/**
* @param entityList 要转换的数据
* @param primaryFieldName 主键ID
* @param parentFieldName 父ID
* @param childrenName 子集合属性名
* @param pidValue 顶级父ID值
* @return 树形结构list
*/
@SuppressWarnings("unchecked")
public List<T> listToTree(List<?> entityList, String primaryFieldName, String parentFieldName, String childrenName, String pidValue) {
if (CollectionUtil.isEmpty(entityList)) {
return new ArrayList<>();
}
Object o = entityList.get(0);
if (StrUtil.isNotBlank(primaryFieldName) && StrUtil.isNotBlank(parentFieldName)) {
primaryFieldName = PRIMARY_FIELD_NAME;
parentFieldName = PARENT_FIELD_NAME;
} else {
Class<?> aClass = o.getClass();
Field[] declaredFields = aClass.getDeclaredFields();
for (Field field : declaredFields) {
String name = field.getName();
if (name.endsWith(PRIMARY_FIELD_ENDS_WITH)) {
parentFieldName = name;
primaryFieldName = parentFieldName.substring(0, parentFieldName.lastIndexOf(PRIMARY_FIELD_ENDS_WITH)) + PARENT_FIELD_ENDS_WITH;
}
}
}
if (StrUtil.isBlank(childrenName)) {
childrenName = CHILDREN_LIST;
}
if (StrUtil.isNotBlank(pidValue)) {
pidValue = PID_VALUE;
}
//返回的map Tree树形结构
List<Map<String, Object>> treeMap = new ArrayList<>();
//将传进的参数entityList转为MapList
List<Map<String, Object>> listMap = JSON.parseObject(JSON.toJSONString(entityList), List.class);
//声明一个map用来存listMap中的对象,key为对象id,value为对象本身
Map<String, Map<String, Object>> entityMap = new Hashtable<>();
//循环listMap把map对象put到entityMap中去
for (Map<String, Object> map : listMap) {
entityMap.put(map.get(primaryFieldName).toString(), map);
}
//循环listMap进行Tree树形结构组装
for (Map<String, Object> map : listMap) {
//获取map的pid
Object pid = map.get(parentFieldName);
//判断pid是否为空或者为0,为空说明是最顶级,直接add到返回的treeMap中去
if (pid == null || StrUtil.equals(pid.toString(), pidValue)) {
treeMap.add(map);
} else {
//如果pid不为空也不为0,是子集
// 根据当前map的pid获取上级 parentMap
Map<String, Object> parentMap = entityMap.get(pid.toString());
if (parentMap == null) { //如果parentMap为空,则说明当前map没有父级,当前map就是顶级
treeMap.add(map);
} else {
//如果parentMap不为空,则当前map为parentMap的子级
//取出parentMap的所有子级的List集合
List<Map<String, Object>> children = (List<Map<String, Object>>) parentMap.get(childrenName);
if (children == null) { //判断子级集合是否为空,为空则新创建List
children = new ArrayList<>();
parentMap.put(childrenName, children);
}
//把当前map对象add到parentMap的子级List中去
children.add(map);
}
}
}
return JSONUtil.toList(String.valueOf(treeMap), null);
}
public List<T> listToTree(List<?> entityList) {
return listToTree(entityList, "", "", "", "");
}
public List<T> listToTree(List<?> entityList, String primaryFieldName, String parentFieldName) {
return listToTree(entityList, primaryFieldName, parentFieldName, "", "");
}
public List<T> listToTree(List<?> entityList, String primaryFieldName, String parentFieldName, String childrenName) {
return listToTree(entityList, primaryFieldName, parentFieldName, childrenName, "");
}