樹形結構數據存儲方案的選擇和java list轉tree


樹形結構數據存儲方案

Adjacency List:每一條記錄存parent_id
Path Enumerations:每一條記錄存整個tree path經過的node枚舉
Nested Sets:每一條記錄存 nleft 和 nright
Closure Table:維護一個表,所有的tree path作為記錄進行保存。

各種方法的常用操作代價見下圖

 

 
一般來說,數據量小,采用適合鄰接表存儲設計,簡單靈活,而大部分情況下都不會有太大的數據,主要用於種類樹、菜單樹。

鄰接表再程序中的使用:直接查詢所有,然后構建樹形結構數據。有序數據構建樹,層級之間是有序的。可通過sql查詢排序。

 

java list轉tree

TreeNode接口

 

package klg.common.tree;

import java.io.Serializable;
import java.util.List;
/**
 * 
 * @author klguang
 *
 * @param <ID>
 */
public interface TreeNode<ID extends Serializable> {

    public ID getId();
    public ID getParentId();
    
    public <T extends TreeNode<ID>> void setChildren(List<T> children);
    
}

  

TreeHelper工具類

package klg.common.tree;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;
/**
 * 
 * @author klguang
 *
 */
public class TreeHelper {

    /**
     * 
     * @param parentID
     *            null 為根節點
     * @param nodeList
     * @param sort
     * @return
     */
    public static <ID extends Serializable,T extends TreeNode<ID>> List<T> buildTree(ID parentID, List<T> nodeList) {
        // 根節點列表
        List<T> list = new ArrayList<>();
        // 順序遍歷節點列表,如果之前是有序的,那么構建樹后同層級之間有序
        for (int i=0; i<nodeList.size(); i++) {
            T node = nodeList.get(i);
            //遞歸入口, String.valueOf防止null值
            if (String.valueOf(node.getParentId()).equals(String.valueOf(parentID))) {
                // parentID作為入口
                List<T> children = buildTree(node.getId(), nodeList);
                node.setChildren(children);
                list.add(node);
            }
        }
        
        return list;
    }        
}

  

案例easyui tree

package klg.common.tree;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import javax.persistence.Access;
import javax.persistence.AccessType;
import javax.persistence.Column;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.MappedSuperclass;
import javax.persistence.Transient;

/**
 * 
 * @author klguang
 *
 */
@MappedSuperclass
@Access(AccessType.FIELD)
public abstract class EasyUITreeNode<ID extends Serializable> implements Serializable, TreeNode<ID> {

    private static final long serialVersionUID = 850845227481354764L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private ID id;

    @Column(name = "parent_id")
    private ID parentId;

    @Column(name = "name", nullable = false)
    private String name;

    @Column(name = "icon_cls")
    private String iconCls;

    @Column(name = "state")
    private String state;

    @Column(name = "order_num")
    private Integer orderNum;

    @SuppressWarnings("rawtypes")
    @Transient
    List children = new ArrayList<>();

    /**
     * easyui treegrid 需求格式
     * 
     * @return
     */
    public String getText() {
        return this.name;
    }

    public ID getId() {
        return id;
    }

    public void setId(ID id) {
        this.id = id;
    }

    public ID getParentId() {
        return parentId;
    }

    public void setParentId(ID parentId) {
        this.parentId = parentId;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getIconCls() {
        return iconCls;
    }

    public void setIconCls(String iconCls) {
        this.iconCls = iconCls;
    }

    public String getState() {
        return state;
    }

    public void setState(String state) {
        this.state = state;
    }

    public Integer getOrderNum() {
        return orderNum;
    }

    public void setOrderNum(Integer orderNum) {
        this.orderNum = orderNum;
    }

    @SuppressWarnings("unchecked")
    public <T extends TreeNode<ID>> List<T> getChildren() {
        return children;
    }

    public<T extends TreeNode<ID>> void setChildren(List<T> children) {
        this.children = children;
    }

}

  

使用方法

easyui tree實現類

public class Permission extends EasyUITreeNode<Long> {
    //fields
}

構建樹

    public List<Permission> findAll(){
        Sort sort = new Sort(Direction.ASC,"orderNum");
        List<Permission> listData=permissionService.findList(sort);
        
        return TreeHelper.<Long,Permission>buildTree(null, listData);
    }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM