有时候我们项目里面需要将树型关系的数据转换成Json格式的String字符串

假设数据库中的数据如下

需要转换后输出的字符串的结果如下(对应的层级的关系)

[

  {name:'爷爷',id:'1',content:'老人辈',parentId:'0',expanded: true,children:[

    {name:'爸爸',id:'2',content:'长辈',parentId:'1',expanded: true,children:[

          {name:'儿子',id:'4',content:'晚辈',parentId:'2',leaf:true},{name:'女儿',id:'5',content:'晚辈',parentId:'2',leaf:true}

       ]},{name:'叔叔',id:'3',content:'长辈',parentId:'1',leaf:true}
]
}
]

相应的代码资料网上可以找到

1、树节点类

 import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map; /**
* 树节点类(用于模拟树型结构关系中的节点)
*/
public class TreeNode {
public static final String TREENODE_ATTRIBUTE_NAME_NAME = "name"; // 字段属性name
public static final String TREENODE_ATTRIBUTE_NAME_ID = "id"; // 字段属性id
private Map<String,Object> attributes = new HashMap<String, Object>(); // 字段属性的Map private TreeNode parent = null; //当前节点的父节点
private List<TreeNode> child = new ArrayList<TreeNode>(); //当前节点的子节点
private boolean isCheck = false; //当前节点是否被勾选标志 /*
无参构造函数
*/
public TreeNode(){
super();
} /**
* 获取/设置 节点的属性name
* @return
*/
public String getName() {
return (String) attributes.get(TREENODE_ATTRIBUTE_NAME_NAME);
}
public void setName(String name) {
attributes.put(TREENODE_ATTRIBUTE_NAME_NAME,name);
} /**
* 获取/设置 节点的属性id
* @return
*/
public String getId() {
return (String) attributes.get(TREENODE_ATTRIBUTE_NAME_ID);
}
public void setId(String id) {
attributes.put(TREENODE_ATTRIBUTE_NAME_ID,id);
} /**
* 获取/设置 节点需要在树形结构中显示的信息
* @return
*/
public Map<String, Object> getAttributes() {
return attributes;
}
public void setAttributes(Map<String, Object> attributes) {
this.attributes = attributes;
} /**
* 获取/设置 节点是否被勾选信息
* @return
*/
public boolean isCheck() {
return isCheck;
}
public void setCheck(boolean check) {
isCheck = check;
} /**
* 获取/设置 节点父节点信息
* @return
*/
public TreeNode getParent() {
return parent;
}
public void setParent(TreeNode parent) {
this.parent = parent;
} /**
* 是否存在/获取/设置/添加 节点子节点信息
* @return
*/
public boolean hasChildren(){
return child.size()>0;
}
public List<TreeNode> getChild() {
return child;
}
public void setChild(List<TreeNode> child) {
this.child = child;
}
public void addChild(TreeNode treeNode){
treeNode.setParent(this);
child.add(treeNode);
}
}

2、树型节点的属性Map类

 import java.util.HashMap;
import java.util.Map; /**
* 树型节点的属性Map(用于操作节点的各个属性,如name,id)
*/
public class TreeAttributesMap {
private Map<String,Object> attributes = new HashMap<>(); //存放属性的Map /**
* 有参构造函数
* @param id
* @param name
*/
public TreeAttributesMap(Object id,Object name){
attributes.put(TreeNode.TREENODE_ATTRIBUTE_NAME_ID,id);
attributes.put(TreeNode.TREENODE_ATTRIBUTE_NAME_NAME,name);
} /**
* 获取属性的Map
* @return
*/
public Map<String, Object> getAttributes() {
return attributes;
} /**
* 往属性的Map中添加属性
* @param name
* @param value
*/
public void putAttributes(String name,Object value){
attributes.put(name,value);
}
}

3、定义一些树型结构相关的接口(方便以后拓展)

 /**
* 定义一般普通的树节点的接口
*/
public interface ISimpleTreeNode { /**
* 每个树节点都具备自身的一些属性
* @return
*/
public TreeAttributesMap getTreeAttributesMap();
}
 /**
* 定义层级树节点的接口
*/
public interface ILevelTreeNode extends ISimpleTreeNode{ public int getParentId();
public int getId();
}
 public interface ITreeParser<T> {
/**
* 解析数据
* @param data
* @return
*/
List<T> parser(Object data);
}

4、树类

 /**
* 树类 (根据自身需求对数据进行解析和转换)
*/
public class Tree {
private ITreeParser<TreeNode> treeParser;
private int treeType; //转换标志(可以拓展)
private Object data; //数据源 /**
* 有参构造函数
* @param data
* @param treeType
*/
public Tree(Object data,int treeType){
this.data = data;
this.treeType = treeType;
} /**
* 数据转换 data ---> json格式
* @return json格式的String
*/
public String toJsonTree(){
String json = "";
if (treeType == 1){
treeParser = new LevelTreeParser();
json = toLevelTree();
}else if (treeType == 2){
//XXX树型结构
}else if (treeType == 3){
//XXX树型结构
}else{
//other树型结构
}
return json;
} private String toLevelTree(){
String jsonString = "";
List<TreeNode> nodes = treeParser.parser(data);
StringBuffer sb = new StringBuffer();
sb.append("[");
parserLevelNodeToJson(sb,nodes);
sb.append("]");
jsonString = sb.toString();
return jsonString;
} private void parserLevelNodeToJson(StringBuffer sb,List<TreeNode> nodes){
Iterator<TreeNode> it = nodes.iterator();
while(it.hasNext()){
TreeNode node = it.next();
boolean isLeaf = node.hasChildren();
sb.append("{");
Map<String,Object> attributes = node.getAttributes();
for(String key:attributes.keySet()){
Object obj = attributes.get(key);
if (obj != null)
sb.append(key + ":'" + obj.toString() + "',");
}
if (isLeaf){
sb.append("expanded: true,children: [");
parserLevelNodeToJson(sb,node.getChild());
if (it.hasNext()){
sb.append("]},");
}else{
sb.append("]}");
}
}else{
if (it.hasNext()){
sb.append("leaf:true},");
}else{
sb.append("leaf:true}");
}
}
}
}
}

5、层级树状结构解析实现类

 import java.util.HashMap;
import java.util.List;
import java.util.Map; public class LevelTreeParser implements ITreeParser<TreeNode>{ private Map<Object,TreeNode> treeNodeMap = new HashMap<Object, TreeNode>();
TreeNode root = new TreeNode(); public List<TreeNode> parser(Object data){
//将数据data强转为List<ILevelTreeNode>格式
List<ILevelTreeNode> list = (List<ILevelTreeNode>) data;
//List<TreeNode> nodes = new ArrayList<TreeNode>(); //list不为空且大小不为0
if (list != null && list.size()>0){ //加强for循环list
for (ILevelTreeNode levelTreeNode:list){
TreeNode item = new TreeNode();
//获取每个树节点的属性
item.setAttributes(levelTreeNode.getTreeAttributesMap().getAttributes());
//封装每个树节点
treeNodeMap.put(levelTreeNode.getId(),item);
}
//再次遍历所有的树节点
for (ILevelTreeNode levelTreeNode:list){
TreeNode parent = treeNodeMap.get(levelTreeNode.getParentId());
TreeNode treeNode = treeNodeMap.get(levelTreeNode.getId());
if (parent == null){
root.addChild(treeNode);
}else{
parent.addChild(treeNode);
}
}
}
return root.getChild();
}
}

6、解析格式选择类

 /**
* 解析格式选择类 (用于接受数据源并选择解析格式)
*/
public class BaseParser {
public static String parserListToLevelTree(List list){
Tree tree = new Tree(list,1);
return tree.toJsonTree();
}
}

7、数据库的Model类treeLevel

要实现接口ILevelTreeNode并实现getTreeAttributesMap的方法,把数据库字段对应的类中的属性都封装起来

 public class treeLevel implements ILevelTreeNode {

     private int id;
private int parentId;
private String name;
private String content; @Override
public int getId() {
return id;
} public void setId(int id) {
this.id = id;
} @Override
public int getParentId() {
return parentId;
} public void setParentId(int parentId) {
this.parentId = parentId;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public String getContent() {
return content;
} public void setContent(String content) {
this.content = content;
} @Override
public TreeAttributesMap getTreeAttributesMap() {
TreeAttributesMap treeMap = new TreeAttributesMap(this.id,this.name);
treeMap.putAttributes("content",this.content);
treeMap.putAttributes("parentId",this.parentId);
return treeMap;
}
}

8、Dao层(查询数据库表中所有的记录)

 @Mapper
public interface MyDao { @Select("SELECT * FROM treelevel")
4 List<treeLevel> getTreeLevelList();
5 }

9、Server层就省略了,最后只要在Controller层提供Server层调用Dao层访问数据库,将返回的结果List传入静态方法BaseParser.parserListToLevelTree()中即可。

最后,总结一下

a.先为自己的树型节点定义好接口,比如每个节点有获取自己的id、父节点id、属性集合等方法。

b.根据数据库字段创建好对应的类的Model,这里Model类需要实现之前定义好节点的接口,便于后面代码的接入。

c.创建好Parser转换类,将传入List形式的数据转换成自己想要的节点链表形式的数据(对每个节点封装好父节点、子节点们和自身属性集合等)。

d.创建好Tree数据选择解析类,将转换好的节点数据集合解析成自己想要的Json格式的String字符串。

将数据转换成树型层级的Json格式的String的更多相关文章

  1. 从一个复杂的json格式的String内获取某key的值

    如题,如何简单的从一个复杂的String格式内获取某个key的值. 例如:从下面String下取到status的值. {"response":{"info":{ ...

  2. Python把json格式的string对象转变成dict对象操作、Python3不能使用urllib2、urllib.parse.urlencode(params).encode(encoding='UTF8')

    son格式的string对象转变成dict对象操作 content=eval(content)#json字典转化 Python3不能使用urllib2 直接使用urllib.request替换urll ...

  3. Json格式转换

    验证Json格式可以进入 http://json.cn/ json简单说就是javascript中的对象和数组,所以这两种结构就是对象和数组两种结构,通过这两种结构可以表示各种复杂的结构1.对象:对象 ...

  4. json格式转换成Map的应用

    jsp 1.引用json.js(将json格式转换成字符串) 2. var name = document.getElementById("name").value; var re ...

  5. 转!!JavaBean,List,Map转成json格式

    public class User { private String username; private String password; public String getUsername() { ...

  6. JavaBean,List,Map转成json格式

    public class User { private String username; private String password; public String getUsername() { ...

  7. Ajax中的JSON格式与php传输过程的浅析

    在Ajax中的JSON格式与php传输过程中有哪些要注意的小地方呢? 先来看一下简单通用的JSON与php传输数据的代码 HTML文件: <input type="button&quo ...

  8. JSON(五)——同步请求中使用JSON格式字符串进行交互(不太常见的用法)

    在同步请求中使用JSON格式进行数据交互的场景并不多,同步请求是浏览器直接与服务器进行数据交互的大多是用jsp的标签jstl和el表达式对请求中的数据进行数据的渲染.我也是在一次开发中要从其它服务器提 ...

  9. xml和JSON格式相互转换的Java实现

    依赖的包: json-lib-2.4-jdk15.jar ezmorph-1.0.6.jar xom-1.2.1.jar commons-lang-2.1.jar commons-io-1.3.2.j ...

随机推荐

  1. vue-详情列表偷懒遍历

    假如数据格式是这样的: 文案的字段名和数据的字段名完全对应,我们在处理数据的时候,就可以用: 完美:

  2. redis 持久化共享 Session

    https://docs.microsoft.com/zh-cn/azure/redis-cache/cache-aspnet-session-state-provider

  3. 7、TypeScript数据类型

    1.变量声明 var 不要使用 建议使用: let 变量 const 常量,一旦申明不能修改 2.数据类型 2.1布尔值:boolean 2.2数字类型  :number 2.3字符串类型:strin ...

  4. 从安装Mac OS X虚拟机到第一个IOS程序

    对于纯粹地抄这种行为是比较抵触的,别人已经写得挺好的东西没必要又去写一遍,但如果不写经验来看下次再做时自己又要重复百度筛选一遍,所以还是要记一记. 之前要获取IOS静态库的版本,但一直以来没有Mac没 ...

  5. MSDN订户下载权限被屏蔽的办法

    使用Chrome浏览器,在加载完成页面之后,按F12,在控制台选项卡当中输入下面代码,即可解除屏蔽. $("#SubMigratedMessageArea").remove(); ...

  6. Vue.js学习过程

    打开各大论坛,看到好多Vue.js的话题,可以说现在是非常火的框架,看到一个人这样评论Vue:“Vue.js兼容angular.js和 react.js的优点,并剔除他们的缺点.”因为现在公司不用Vu ...

  7. ClientDataSet应用

    最近维护一个项目,里面用到ClientDataSet,由于之前接触ClientDataSet比较少,所以这个星期补了一下关于ClientDataSet的知识,并在此记录下我所了解到的并应用到实际项目中 ...

  8. 跟随我在oracle学习php(10)

    正则表达式 做验证 做匹配 用符号来描述书写规则:/ 中间写正则表达式 /^ :匹配开头,$:匹配结尾 : /^ve/以ve开头的 /ve$/以ve结尾\d:一个任意的数字\w:一个任意的数字或字母\ ...

  9. [数]数学系列预习->补水题ver.

    ---恢复内容开始--- 话说要学反演了,contest一题都搞不定,整理题目暂且搁置,数学笨蛋来学一下数学_(:з」∠)_ ---恢复内容结束--- 是的,预习看了半天教学,没有整理,做题又都不会, ...

  10. js-notebook

    注意DOM和BOM的区别,ECMAScript只针对js的语法核心,实际大部分浏览器里的js = ECMAScript + DOM + BOM, 而nodejs里就只包括core js 隐性的toSt ...