Java tree data-structure?
有一个好的可用(标准Java)数据结构来表示Java中的树吗?
具体来说,我需要代表以下内容:
- 任何节点上的树都可以有任意数量的子级
- 每个节点(在根之后)只是一个字符串(其子节点也是字符串)
- 我需要能够让所有的子节点(某种列表或字符串数组)都得到一个表示给定节点的输入字符串。
是否有可用的结构来解决这个问题,或者我是否需要创建自己的结构(如果是这样的话,实现建议会很好)。
在这里:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | public class Tree<T> { private Node<T> root; public Tree(T rootData) { root = new Node<T>(); root.data = rootData; root.children = new ArrayList<Node<T>>(); } public static class Node<T> { private T data; private Node<T> parent; private List<Node<T>> children; } } |
这是一个基本的树结构,可以用于
您需要添加的只是用于添加到、移除、遍历和构造函数的方法。
还有另一种树结构:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | public class TreeNode<T> implements Iterable<TreeNode<T>> { T data; TreeNode<T> parent; List<TreeNode<T>> children; public TreeNode(T data) { this.data = data; this.children = new LinkedList<TreeNode<T>>(); } public TreeNode<T> addChild(T child) { TreeNode<T> childNode = new TreeNode<T>(child); childNode.parent = this; this.children.add(childNode); return childNode; } // other features ... } |
样品使用情况:
1 2 3 4 5 6 7 8 9 10 11 12 13 | TreeNode<String> root = new TreeNode<String>("root"); { TreeNode<String> node0 = root.addChild("node0"); TreeNode<String> node1 = root.addChild("node1"); TreeNode<String> node2 = root.addChild("node2"); { TreeNode<String> node20 = node2.addChild(null); TreeNode<String> node21 = node2.addChild("node21"); { TreeNode<String> node210 = node20.addChild("node210"); } } } |
奖金见完全羽化的树:
- 迭代器
- 搜索
- 爪哇/ C
https://github.com/gt4dev/yet-another-tree-structure
实际上,JDK中实现了一个非常好的树结构。
看看javax.swing.tree、treemodel和treenode。它们被设计为与
注意,对于Java 9,您可能不希望使用这些类,因为它们将不存在于"紧凑配置文件"中。
这个怎么样?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 | import java.util.ArrayList; import java.util.Collection; import java.util.HashMap; /** * @author [email protected] (Yohann Coppel) * * @param <T> * Object's type in the tree. */ public class Tree<T> { private T head; private ArrayList<Tree<T>> leafs = new ArrayList<Tree<T>>(); private Tree<T> parent = null; private HashMap<T, Tree<T>> locate = new HashMap<T, Tree<T>>(); public Tree(T head) { this.head = head; locate.put(head, this); } public void addLeaf(T root, T leaf) { if (locate.containsKey(root)) { locate.get(root).addLeaf(leaf); } else { addLeaf(root).addLeaf(leaf); } } public Tree<T> addLeaf(T leaf) { Tree<T> t = new Tree<T>(leaf); leafs.add(t); t.parent = this; t.locate = this.locate; locate.put(leaf, t); return t; } public Tree<T> setAsParent(T parentRoot) { Tree<T> t = new Tree<T>(parentRoot); t.leafs.add(this); this.parent = t; t.locate = this.locate; t.locate.put(head, this); t.locate.put(parentRoot, t); return t; } public T getHead() { return head; } public Tree<T> getTree(T element) { return locate.get(element); } public Tree<T> getParent() { return parent; } public Collection<T> getSuccessors(T root) { Collection<T> successors = new ArrayList<T>(); Tree<T> tree = getTree(root); if (null != tree) { for (Tree<T> leaf : tree.leafs) { successors.add(leaf.head); } } return successors; } public Collection<Tree<T>> getSubTrees() { return leafs; } public static <T> Collection<T> getSuccessors(T of, Collection<Tree<T>> in) { for (Tree<T> tree : in) { if (tree.locate.containsKey(of)) { return tree.getSuccessors(of); } } return new ArrayList<T>(); } @Override public String toString() { return printTree(0); } private static final int indent = 2; private String printTree(int increment) { String s =""; String inc =""; for (int i = 0; i < increment; ++i) { inc = inc +""; } s = inc + head; for (Tree<T> child : leafs) { s +=" " + child.printTree(increment + indent); } return s; } } |
我写了一个处理普通树的小库。它比秋千轻得多。我也有一个Maven项目。
1 2 3 4 5 6 7 8 9 10 |
显然,您可以添加实用程序方法来添加/删除子项。
您应该首先定义树是什么(对于域),最好先定义接口。并不是所有的树结构都是可修改的,能够添加和删除节点应该是一个可选的特性,所以我们为此做了一个额外的接口。
不需要创建保存值的节点对象,事实上,我认为这是大多数树实现中的一个主要设计缺陷和开销。如果你看Swing,
1 2 3 4 5 | public interface Tree <N extends Serializable> extends Serializable { List<N> getRoots (); N getParent (N node); List<N> getChildren (N node); } |
可变树结构(允许添加和删除节点):
1 2 3 4 | public interface MutableTree <N extends Serializable> extends Tree<N> { boolean add (N parent, N node); boolean remove (N node, boolean cascade); } |
考虑到这些接口,使用树的代码不必太关心树是如何实现的。这允许您使用通用实现和专用实现,通过将函数委托给另一个API来实现树。
示例:文件树结构
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | public class FileTree implements Tree<File> { @Override public List<File> getRoots() { return Arrays.stream(File.listRoots()).collect(Collectors.toList()); } @Override public File getParent(File node) { return node.getParentFile(); } @Override public List<File> getChildren(File node) { if (node.isDirectory()) { File[] children = node.listFiles(); if (children != null) { return Arrays.stream(children).collect(Collectors.toList()); } } return Collections.emptyList(); } } |
示例:通用树结构(基于父/子关系):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 | public class MappedTreeStructure<N extends Serializable> implements MutableTree<N> { public static void main(String[] args) { MutableTree<String> tree = new MappedTreeStructure<>(); tree.add("A","B"); tree.add("A","C"); tree.add("C","D"); tree.add("E","A"); System.out.println(tree); } private final Map<N, N> nodeParent = new HashMap<>(); private final LinkedHashSet<N> nodeList = new LinkedHashSet<>(); private void checkNotNull(N node, String parameterName) { if (node == null) throw new IllegalArgumentException(parameterName +" must not be null"); } @Override public boolean add(N parent, N node) { checkNotNull(parent,"parent"); checkNotNull(node,"node"); // check for cycles N current = parent; do { if (node.equals(current)) { throw new IllegalArgumentException(" node must not be the same or an ancestor of the parent"); } } while ((current = getParent(current)) != null); boolean added = nodeList.add(node); nodeList.add(parent); nodeParent.put(node, parent); return added; } @Override public boolean remove(N node, boolean cascade) { checkNotNull(node,"node"); if (!nodeList.contains(node)) { return false; } if (cascade) { for (N child : getChildren(node)) { remove(child, true); } } else { for (N child : getChildren(node)) { nodeParent.remove(child); } } nodeList.remove(node); return true; } @Override public List<N> getRoots() { return getChildren(null); } @Override public N getParent(N node) { checkNotNull(node,"node"); return nodeParent.get(node); } @Override public List<N> getChildren(N node) { List<N> children = new LinkedList<>(); for (N n : nodeList) { N parent = nodeParent.get(n); if (node == null && parent == null) { children.add(n); } else if (node != null && parent != null && parent.equals(node)) { children.add(n); } } return children; } @Override public String toString() { StringBuilder builder = new StringBuilder(); dumpNodeStructure(builder, null,"-"); return builder.toString(); } private void dumpNodeStructure(StringBuilder builder, N node, String prefix) { if (node != null) { builder.append(prefix); builder.append(node.toString()); builder.append(' '); prefix =" " + prefix; } for (N child : getChildren(node)) { dumpNodeStructure(builder, child, prefix); } } } |
没有答案提到过简化的工作代码,所以这里是:
1 2 3 4 | public class TreeNodeArray<T> { public T value; public final java.util.List<TreeNodeArray<T>> kids = new java.util.ArrayList<TreeNodeArray<T>>(); } |
您可以使用Java的任何XML API作为文档和节点,因为XML是一个带字符串的树结构。
在Java中有一些树数据结构,例如JDK Swing中的Debug ToMababeleReNoDE、斯坦福解析器包中的树和其他玩具代码。但这些都不足以满足一般用途。
Java树项目试图在Java中提供另一种通用树数据结构。这个和其他的区别是
- 完全免费。你可以在任何地方使用它(家庭作业除外:p)
- 小而一般。我将数据结构的所有内容都放在一个类文件中,这样就很容易复制/粘贴。
- 不仅仅是玩具。我知道几十个Java树代码,只能处理二叉树或有限的操作。这棵树结比那要多得多。它提供了不同的访问节点的方法,如预排序、后排序、breadthfirst、leaves、根路径等,并且还提供了迭代器以充分利用这些方法。
- 将添加更多的实用程序。我愿意增加更多的操作来使这个项目更全面,特别是如果你通过GitHub发送一个请求。
按照加雷斯的回答,查看默认可变树型。它不是通用的,但在其他方面似乎符合这个要求。即使它在javax.swing包中,它也不依赖于任何awt或swing类。实际上,源代码实际上有注释
如果你在做白板编码,面试,甚至只是打算用一棵树,这些都有点冗长。
还应该说,树不在其中的原因,比如说,
1 2 3 4 5 6 7 8 | /*** /* Within the class that's using a binary tree for any reason. You could /* generalize with generics IFF the parent class needs different value types. */ private class Node { public String value; public Node[] nodes; // Or an Iterable<Node> nodes; } |
这真的适用于任意宽度的树。
如果需要二叉树,通常更容易与命名字段一起使用:
1 2 3 4 5 | private class Node { // Using package visibility is an option String value; Node left; Node right; } |
或者如果你想要一个特里尔:
1 2 3 4 |
现在你说你想要
to be able to get all the children (some sort of list or array of Strings) given an input string representing a given node
听起来像你的家庭作业。不过,既然我有理由确定现在已经过了最后期限…
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 | import java.util.Arrays; import java.util.ArrayList; import java.util.List; public class kidsOfMatchTheseDays { static private class Node { String value; Node[] nodes; } // Pre-order; you didn't specify. static public List<String> list(Node node, String find) { return list(node, find, new ArrayList<String>(), false); } static private ArrayList<String> list( Node node, String find, ArrayList<String> list, boolean add) { if (node == null) { return list; } if (node.value.equals(find)) { add = true; } if (add) { list.add(node.value); } if (node.nodes != null) { for (Node child: node.nodes) { list(child, find, list, add); } } return list; } public static final void main(String... args) { // Usually never have to do setup like this, so excuse the style // And it could be cleaner by adding a constructor like: // Node(String val, Node... children) { // value = val; // nodes = children; // } Node tree = new Node(); tree.value ="root"; Node[] n = {new Node(), new Node()}; tree.nodes = n; tree.nodes[0].value ="leftish"; tree.nodes[1].value ="rightish-leafy"; Node[] nn = {new Node()}; tree.nodes[0].nodes = nn; tree.nodes[0].nodes[0].value ="off-leftish-leaf"; // Enough setup System.out.println(Arrays.toString(list(tree, args[0]).toArray())); } } |
这样你就可以像:
1 2 3 4 5 6 7 8 | $ java kidsOfMatchTheseDays leftish [leftish, off-leftish-leaf] $ java kidsOfMatchTheseDays root [root, leftish, off-leftish-leaf, rightish-leafy] $ java kidsOfMatchTheseDays rightish-leafy [rightish-leafy] $ java kidsOfMatchTheseDays a [] |
1 2 3 4 5 6 7 8 9 10 | public abstract class Node { List<Node> children; public List<Node> getChidren() { if (children == null) { children = new ArrayList<>(); } return chidren; } } |
简单易用。要使用它,请扩展它:
由于问题要求提供可用的数据结构,因此可以从列表或数组构造树:
1 2 3 4 5 6 7 8 |
例如:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 | import java.util.ArrayList; import java.util.List; /** * * @author X2 * * @param <T> */ public class HisTree<T> { private Node<T> root; public HisTree(T rootData) { root = new Node<T>(); root.setData(rootData); root.setChildren(new ArrayList<Node<T>>()); } } class Node<T> { private T data; private Node<T> parent; private List<Node<T>> children; public T getData() { return data; } public void setData(T data) { this.data = data; } public Node<T> getParent() { return parent; } public void setParent(Node<T> parent) { this.parent = parent; } public List<Node<T>> getChildren() { return children; } public void setChildren(List<Node<T>> children) { this.children = children; } } |
我写了一个基于"hashmap"的小"treemap"类,它支持添加路径:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | import java.util.HashMap; import java.util.LinkedList; public class TreeMap<T> extends LinkedHashMap<T, TreeMap<T>> { public void put(T[] path) { LinkedList<T> list = new LinkedList<>(); for (T key : path) { list.add(key); } return put(list); } public void put(LinkedList<T> path) { if (path.isEmpty()) { return; } T key = path.removeFirst(); TreeMap<T> val = get(key); if (val == null) { val = new TreeMap<>(); put(key, val); } val.put(path); } } |
它可以用于存储"t"(通用)类型的树,但不支持在其节点中存储额外的数据。如果您有这样的文件:
1 2 3 4 5 | root, child 1 root, child 1, child 1a root, child 1, child 1b root, child 2 root, child 3, child 3a |
然后,您可以通过执行以下操作使其成为树:
1 2 3 4 5 | TreeMap<String> root = new TreeMap<>(); Scanner scanner = new Scanner(new File("input.txt")); while (scanner.hasNextLine()) { root.put(scanner.nextLine().split(",")); } |
你会得到一棵漂亮的树。它应该很容易适应你的需要。
在过去,我只是使用了一个嵌套的映射。这是我今天用的,很简单,但它符合我的需要。也许这对另一个有用。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 | import com.fasterxml.jackson.annotation.JsonValue; import com.fasterxml.jackson.databind.ObjectMapper; import java.util.HashMap; import java.util.Map; import java.util.TreeMap; /** * Created by kic on 16.07.15. */ public class NestedMap<K, V> { private final Map root = new HashMap<>(); public NestedMap<K, V> put(K key) { Object nested = root.get(key); if (nested == null || !(nested instanceof NestedMap)) root.put(key, nested = new NestedMap<>()); return (NestedMap<K, V>) nested; } public Map.Entry<K,V > put(K key, V value) { root.put(key, value); return (Map.Entry<K, V>) root.entrySet().stream().filter(e -> ((Map.Entry) e).getKey().equals(key)).findFirst().get(); } public NestedMap<K, V> get(K key) { return (NestedMap<K, V>) root.get(key); } public V getValue(K key) { return (V) root.get(key); } @JsonValue public Map getRoot() { return root; } public static void main(String[] args) throws Exception { NestedMap<String, Integer> test = new NestedMap<>(); test.put("a").put("b").put("c", 12); Map.Entry<String, Integer> foo = test.put("a").put("b").put("d", 12); test.put("b", 14); ObjectMapper mapper = new ObjectMapper(); System.out.println(mapper.writeValueAsString(test)); foo.setValue(99); System.out.println(mapper.writeValueAsString(test)); System.out.println(test.get("a").get("b").getValue("d")); } } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 | // TestTree.java // A simple test to see how we can build a tree and populate it // import java.awt.*; import java.awt.event.*; import javax.swing.*; import javax.swing.tree.*; public class TestTree extends JFrame { JTree tree; DefaultTreeModel treeModel; public TestTree( ) { super("Tree Test Example"); setSize(400, 300); setDefaultCloseOperation(EXIT_ON_CLOSE); } public void init( ) { // Build up a bunch of TreeNodes. We use DefaultMutableTreeNode because the // DefaultTreeModel can use it to build a complete tree. DefaultMutableTreeNode root = new DefaultMutableTreeNode("Root"); DefaultMutableTreeNode subroot = new DefaultMutableTreeNode("SubRoot"); DefaultMutableTreeNode leaf1 = new DefaultMutableTreeNode("Leaf 1"); DefaultMutableTreeNode leaf2 = new DefaultMutableTreeNode("Leaf 2"); // Build our tree model starting at the root node, and then make a JTree out // of it. treeModel = new DefaultTreeModel(root); tree = new JTree(treeModel); // Build the tree up from the nodes we created. treeModel.insertNodeInto(subroot, root, 0); // Or, more succinctly: subroot.add(leaf1); root.add(leaf2); // Display it. getContentPane( ).add(tree, BorderLayout.CENTER); } public static void main(String args[]) { TestTree tt = new TestTree( ); tt.init( ); tt.setVisible(true); } } |
Java中没有特定的数据结构,适合您的需求。您的需求非常具体,因此需要设计自己的数据结构。查看您的需求,任何人都可以说您需要某种具有特定功能的n元树。您可以按以下方式设计数据结构:
我建议您在类node string value;list children;中编写节点的结构,在另一个nodeUtils类中编写所有其他方法,如search、insert和getchildren,这样您也可以通过树根在特定的树上执行操作,例如:class nodeUtils公共静态节点搜索(node root,string value)//执行bfs并返回node
您可以使用ApacheJMeter中包含的hashtree类,它是雅加达项目的一部分。
hashtree类包含在包org.apache.jorphan.collections中。虽然这个包不是在JMeter项目之外发布的,但是您可以很容易地获得它:
1)下载JMeter源。
2)创建新包。
3)复制到it/src/jorphan/org/apache/jorphan/collections/。除data.java外的所有文件
4)也复制/src/jorphan/org/apache/jorphan/util/jorphanutils.java
5)hashtree可以使用。
我编写了一个树库,它可以很好地使用Java8,并且没有其他依赖项。它还提供了对函数式编程的一些想法的松散解释,并允许您映射/过滤/修剪/搜索整个树或子树。
网址:https://github.com/rutledgepaulv/prune
这个实现在索引方面没有做任何特殊的工作,我也没有偏离递归,所以使用大型树时性能可能会降低,您可能会破坏堆栈。但是如果你只需要一棵小到中等深度的直截了当的树,我认为它足够好用了。它提供了一个健全(基于值)的平等定义,它还具有一个ToString实现,让您可以可视化树!
请检查下面的代码,其中我使用了树数据结构,而不使用集合类。代码可能有缺陷/改进,但请使用此代码仅供参考。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 | package com.datastructure.tree; public class BinaryTreeWithoutRecursion <T> { private TreeNode<T> root; public BinaryTreeWithoutRecursion (){ root = null; } public void insert(T data){ root =insert(root, data); } public TreeNode<T> insert(TreeNode<T> node, T data ){ TreeNode<T> newNode = new TreeNode<>(); newNode.data = data; newNode.right = newNode.left = null; if(node==null){ node = newNode; return node; } Queue<TreeNode<T>> queue = new Queue<TreeNode<T>>(); queue.enque(node); while(!queue.isEmpty()){ TreeNode<T> temp= queue.deque(); if(temp.left!=null){ queue.enque(temp.left); }else { temp.left = newNode; queue =null; return node; } if(temp.right!=null){ queue.enque(temp.right); }else { temp.right = newNode; queue =null; return node; } } queue=null; return node; } public void inOrderPrint(TreeNode<T> root){ if(root!=null){ inOrderPrint(root.left); System.out.println(root.data); inOrderPrint(root.right); } } public void postOrderPrint(TreeNode<T> root){ if(root!=null){ postOrderPrint(root.left); postOrderPrint(root.right); System.out.println(root.data); } } public void preOrderPrint(){ preOrderPrint(root); } public void inOrderPrint(){ inOrderPrint(root); } public void postOrderPrint(){ inOrderPrint(root); } public void preOrderPrint(TreeNode<T> root){ if(root!=null){ System.out.println(root.data); preOrderPrint(root.left); preOrderPrint(root.right); } } /** * @param args */ public static void main(String[] args) { // TODO Auto-generated method stub BinaryTreeWithoutRecursion <Integer> ls= new BinaryTreeWithoutRecursion <>(); ls.insert(1); ls.insert(2); ls.insert(3); ls.insert(4); ls.insert(5); ls.insert(6); ls.insert(7); //ls.preOrderPrint(); ls.inOrderPrint(); //ls.postOrderPrint(); } } |
可以在Java.UTL.*中使用TeeSeTepe类。它像二进制搜索树一样工作,所以已经排序了。Treeset类实现ITerable、Collection和Set接口。您可以像集合一样使用迭代器遍历树。
1 2 3 4 5 | TreeSet<String> treeSet = new TreeSet<String>(); Iterator<String> it = treeSet.Iterator(); while(it.hasNext()){ ... } |
您可以检查,Java doc和其他一些。
不使用集合框架的树的自定义树实现。它包含树实现中需要的不同的基本操作。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 | class Node { int data; Node left; Node right; public Node(int ddata, Node left, Node right) { this.data = ddata; this.left = null; this.right = null; } public void displayNode(Node n) { System.out.print(n.data +""); } } class BinaryTree { Node root; public BinaryTree() { this.root = null; } public void insertLeft(int parent, int leftvalue ) { Node n = find(root, parent); Node leftchild = new Node(leftvalue, null, null); n.left = leftchild; } public void insertRight(int parent, int rightvalue) { Node n = find(root, parent); Node rightchild = new Node(rightvalue, null, null); n.right = rightchild; } public void insertRoot(int data) { root = new Node(data, null, null); } public Node getRoot() { return root; } public Node find(Node n, int key) { Node result = null; if (n == null) return null; if (n.data == key) return n; if (n.left != null) result = find(n.left, key); if (result == null) result = find(n.right, key); return result; } public int getheight(Node root){ if (root == null) return 0; return Math.max(getheight(root.left), getheight(root.right)) + 1; } public void printTree(Node n) { if (n == null) return; printTree(n.left); n.displayNode(n); printTree(n.right); } } |