将文本转变为Tree

将文本转变为Tree,并统计相应子节点与父节点个数

文本:

B	D	E	F
A	B	C
C	G	H
D
F
H
E	I	J
Z	K
K	L	M	N
N	O	P	Q

效果:
在这里插入图片描述
具体代码:

package com.lgx.other;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.util.*;

/**
 * @author LGX_TvT
 * @date 2020-02-07 17:44
 */
public class Demo {


    public static void main(String[] args) throws Exception {

        File file = new File("E:\\DevelopProjects\\Java_Project\\idea_project\\nlp\\nlp-learn\\src\\main\\java\\com\\lgx\\other\\test2");
        List<TreeNode> treeNodes = createTree(file);
        treeNodes.forEach(tree -> {
            Set<String> nodeData = getAllNodeData(tree, true);
            System.out.println("\n");
            /**
             * 打印树
             */
            printTree(tree, 0);

            /**
             * 子节点
             */
            System.out.println("子节点");
            Map<String, Integer> nextNodeNum = getNextNodeNum(tree, nodeData);
            System.out.println(nextNodeNum);

            /**
             * 父节点
             */
            System.out.println("父节点");
            Map<String, Integer> prevNodeNum = getPrevNodeNum(tree, nodeData);
            System.out.println(prevNodeNum);
        });

    }


    /**
     * 获取文件所有节点
     * @param treeNode
     * @return
     */
    static Set<String> ALL_NODE_DATA = new HashSet<>();
    public static Set<String> getAllNodeData(TreeNode treeNode, boolean isInit) {
        if (isInit) ALL_NODE_DATA.clear();
        if(treeNode != null) {
            ALL_NODE_DATA.add(treeNode.getData());
            for (TreeNode node : treeNode.getNextNode()) {
                getAllNodeData(node, false);
            }
        }
        return ALL_NODE_DATA;
    }

    /**
     * 创建节点树
     * @param file
     * @return
     * @throws Exception
     */
    public static List<TreeNode> createTree(File file) throws Exception {
        TreeNode tree = null; List<TreeNode> treeNodes = new ArrayList<>();
        Map<String, TreeNode> map = new HashMap<>(); String str;
        List<String[]> list = new ArrayList<>();
        try(BufferedReader br = new BufferedReader(new FileReader(file))) {
            while ((str = br.readLine()) != null) {
                String[] split = str.split("\t");
                list.add(split);
                TreeNode treeNode = new TreeNode(split[0], null);
                for (int i = 1; i < split.length; i++) treeNode.addNext(new TreeNode(split[i], treeNode));
                map.put(split[0], treeNode);
            }
        }
        // 合并子树
        merge(map, false);
        merge(map, true);

        System.out.println("生成:" + map.size() + "棵树");
        for (String s : map.keySet()) treeNodes.add(map.get(s));
        return treeNodes;
    }


    /**
     * map子树合并
     * @param map
     */
    public static Map<String, TreeNode> merge(Map<String, TreeNode> map, boolean isMerge) {
        List<String> remove = new ArrayList<>();
        for (String key : map.keySet()) {
            TreeNode treeNode = map.get(key);
            Set<TreeNode> nextNode = treeNode.getNextNode();
            //拼接子树
            List<String> nodeName = new ArrayList<>();
            for (TreeNode node : nextNode) nodeName.add(node.getData());
            for (String s : nodeName) {
                if(map.containsKey(s)) {
                    TreeNode tn = map.get(s);
                    treeNode.getNextNode().remove(new TreeNode(s, null));
                    treeNode.addNext(tn);
                    tn.setPrevNode(treeNode);
                    if(isMerge) remove.add(s);
                }
            }
        }
        if(isMerge) remove.forEach(x -> map.remove(x));
        return map;
    }


    /**
     * 查找单个节点
     */
    public static TreeNode SELECT_TREE_NODE = null;
    public static void getTreeNode(TreeNode tree, String data, boolean isInit) {
        if(isInit) SELECT_TREE_NODE = null;
        if(tree == null) return;
        if(tree.getData().equals(data)) {
            Demo.SELECT_TREE_NODE = tree;
            return;
        }
        if(tree.getNextNode().size() > 0)
            for(TreeNode t : tree.getNextNode()) getTreeNode(t, data, false);
    }


    /**
     * 打印树结构
     * @param tree
     * @param index
     */
    public static void printTree(TreeNode tree, int index) {
        if(tree == null) return;
        for (int i = 0; i < index; i++) System.out.print("\t");
        System.out.println(tree.getData() + " [" + (index == 0 ? "Root" : tree.getPrevNode().getData()) + "]");
        for (TreeNode t : tree.getNextNode()) printTree(t, index + 1);
    }

    /**
     * 获取节点子类个数
     */
    public static Map<String, Integer> getNextNodeNum(TreeNode tree, Set<String> node) {
        Map<String, Integer> map = new HashMap<>();
        node.forEach(x -> {
            getTreeNode(tree, x, true);
            getNodeNextNodeSum(SELECT_TREE_NODE, true);
            map.put(x, NODE_NEXT_NODE_SUM);
        });
        return map;
    }

    /**
     * 统计单个节点子节点
     */
    public static int NODE_NEXT_NODE_SUM = 0;
    public static void getNodeNextNodeSum(TreeNode node, boolean isInit) {
        if (isInit) NODE_NEXT_NODE_SUM = 0;
        if(node == null) return;
        else {
            if(isInit == false) NODE_NEXT_NODE_SUM += 1;
            node.getNextNode().forEach(t -> getNodeNextNodeSum(t, false));
        }
    }

    /**
     * 获取节点父类个数
     */
    public static Map<String, Integer> getPrevNodeNum(TreeNode tree, Set<String> node) {
        Map<String, Integer> map = new HashMap<>();
        node.forEach(x -> {
            // 获取具体节点子树
            getTreeNode(tree, x, true);
            // 获取具体节点父类个数
            getNodePrevNodeSum(SELECT_TREE_NODE, true);
            // 使用 k - v 形式保存
            map.put(x, NODE_PREV_NODE_SUM);
        });
        return map;
    }

    /**
     * 统计单个节点父节点
     */
    public static int NODE_PREV_NODE_SUM = 0;
    public static void getNodePrevNodeSum(TreeNode node, boolean isInit) {
        if (isInit) NODE_PREV_NODE_SUM = 0;
        if(node == null || node.getPrevNode() == null) return;
        NODE_PREV_NODE_SUM += 1;
        getNodePrevNodeSum(node.getPrevNode(), false);
    }
}

/**
 * 树节点
 */
class TreeNode {

    /**
     * 数据
     */
    private String data;

    /**
     * 父节点
     */
    private TreeNode prevNode;

    /**
     * 子节点
     */
    private Set<TreeNode> nextNode = new HashSet<TreeNode>();

    public TreeNode(String data, TreeNode prevNode) {
        this.data = data;
        this.prevNode = prevNode;
    }

    public TreeNode() {
    }

    public void addNext(TreeNode treeNode) {
        this.nextNode.add(treeNode);
    }

    public String getData() {
        return data;
    }

    public void setData(String data) {
        this.data = data;
    }

    public TreeNode getPrevNode() {
        return prevNode;
    }

    public void setPrevNode(TreeNode prevNode) {
        this.prevNode = prevNode;
    }

    public Set<TreeNode> getNextNode() {
        return nextNode;
    }

    public void setNextNode(Set<TreeNode> nextNode) {
        this.nextNode = nextNode;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;
        TreeNode treeNode = (TreeNode) o;
        return data.equals(treeNode.data);
    }

    @Override
    public int hashCode() {
        return data.hashCode();
    }


    @Override
    public String toString() {
        return "TreeNode{" +
                "data='" + data + '\'' +
                ", nextNode=" + nextNode +
                '}';
    }
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值