web-dev-qa-db-fra.com

Java Impression d'un arbre binaire en utilisant Level-Order dans un format spécifique

D'accord, j'ai lu toutes les questions connexes et ne parviens pas à en trouver une qui aide Java. J'ai eu l'idée générale de déchiffrer ce que je peux dans d'autres langues; mais je suis encore à comprendre.

Problème: je voudrais trier par niveau (je travaille en utilisant la récursion) et l’imprimer sous la forme générale d’un arbre.

Alors dis que j'ai ceci:

    1 
   / \
  2   3
 /   / \
4   5   6

Mon code imprime l'ordre des niveaux comme ceci:

1 2 3 4 5 6

Je veux l'imprimer comme ceci:

1
2 3
4 5 6

Maintenant, avant de me donner un discours moral à propos de mon travail ... J'ai déjà terminé mon projet AP Comp Sci et suis curieux à ce sujet lorsque mon professeur a mentionné le sujet Breadth First Search.

Je ne sais pas si cela va aider, mais voici mon code jusqu'à présent:

/**
  * Calls the levelOrder helper method and prints out in levelOrder.
  */
 public void levelOrder()
 {
  q = new QueueList();
  treeHeight = height();
  levelOrder(myRoot, q, myLevel);
 }

 /**
  * Helper method that uses recursion to print out the tree in 
  * levelOrder
  */
 private void levelOrder(TreeNode root, QueueList q, int curLev)
 {
  System.out.print(curLev);
  if(root == null)
  {
   return;
  }

  if(q.isEmpty())
  {
   System.out.println(root.getValue());
  }
  else
  {
   System.out.print((String)q.dequeue()+", ");
  }

  if(root.getLeft() != null)
  {
   q.enqueue(root.getLeft().getValue());
   System.out.println();
  }
  if(root.getRight() != null)
  {
   q.enqueue(root.getRight().getValue());
   System.out.println();
   curLev++;
  }

  levelOrder(root.getLeft(),q, curLev);
  levelOrder(root.getRight(),q, curLev);
 }

D'après ce que je peux comprendre, je devrai utiliser la hauteur totale de l'arbre et utiliser un compteur de niveau ... Le seul problème est que mon compteur de niveau continue de compter lorsque mon niveau utilise la récursivité pour revenir à travers l'arbre.

Désolé si c'est trop, mais quelques conseils seraient bien. :)

17
JavaFail

Voici le code, cette question m'a été posée dans l'une des interviews ...

public void printTree(TreeNode tmpRoot) {

        Queue<TreeNode> currentLevel = new LinkedList<TreeNode>();
        Queue<TreeNode> nextLevel = new LinkedList<TreeNode>();

        currentLevel.add(tmpRoot);

        while (!currentLevel.isEmpty()) {
            Iterator<TreeNode> iter = currentLevel.iterator();
            while (iter.hasNext()) {
                TreeNode currentNode = iter.next();
                if (currentNode.left != null) {
                    nextLevel.add(currentNode.left);
                }
                if (currentNode.right != null) {
                    nextLevel.add(currentNode.right);
                }
                System.out.print(currentNode.value + " ");
            }
            System.out.println();
            currentLevel = nextLevel;
            nextLevel = new LinkedList<TreeNode>();

        }

    }
26
Reddy

C'est la solution la plus simple

public void byLevel(Node root){
     Queue<Node> level  = new LinkedList<>();
     level.add(root);
     while(!level.isEmpty()){
         Node node = level.poll();
         System.out.print(node.item + " ");
         if(node.leftChild!= null)
         level.add(node.leftChild);
         if(node.rightChild!= null)
         level.add(node.rightChild);
     }
}

https://github.com/camluca/Samples/blob/master/Tree.Java Dans mon github, vous pouvez trouver d'autres fonctions utiles dans la classe Tree telles que

Affichage de l'arbre

****......................................................****
                            42
            25                              65                              
    12              37              43              87              
9      13      30      --      --      --      --      99      
****......................................................****
Inorder traversal
9 12 13 25 30 37 42 43 65 87 99  
Preorder traversal
42 25 12 9 13 37 30 65 43 87 99  
Postorder traversal
9 13 12 30 37 25 43 99 87 65 42  
By Level
42 25 65 12 37 43 87 9 13 30 99  
12
Luca

Voici comment je le ferais:

levelOrder(List<TreeNode> n) {
    List<TreeNode> next = new List<TreeNode>();
    foreach(TreeNode t : n) {
        print(t);
        next.Add(t.left);
        next.Add(t.right);
    }
    println();
    levelOrder(next);
}

(À l'origine, ce serait du vrai code - je me suis ennuyé en cours de route, donc c'est psueodocodey)

8
Anon.

Je viens de penser à partager la suggestion d’Anon dans du code Java réel et à résoudre quelques problèmes de clé (comme il n’existe pas de condition de fin pour la récursivité, elle ne cesse donc pas d’ajouter à la pile, et le fait de ne pas rechercher null dans le tableau reçu vous donne la valeur null exception de pointeur).

Il n'y a pas non plus d'exception, comme le suggère Eric Hauser, car il ne modifie pas la collection en boucle, il en modifie une nouvelle.

Ici ça va:

public void levelOrder(List<TreeNode> n) {
    List<TreeNode> next = new ArrayList<TreeNode>();
    for (TreeNode t : n) {
        if (t != null) {
            System.out.print(t.getValue());
            next.add(t.getLeftChild());
            next.add(t.getRightChild());
        }
    }
    System.out.println();
    if(next.size() > 0)levelOrder(next);
}
5
Luis Herrera

La méthode ci-dessous renvoie ArrayList de ArrayList contenant tous les nœuds niveau par niveau: -

 public ArrayList<ArrayList<Integer>> levelOrder(TreeNode root) {

    ArrayList<ArrayList<Integer>> result = new ArrayList<ArrayList<Integer>>(); 
    if(root == null) return result;
    Queue q1 = new LinkedList();
    Queue q2 = new LinkedList();

    ArrayList<Integer> list = new ArrayList<Integer>();
    q1.add(root);

    while(!q1.isEmpty() || !q2.isEmpty()){

        while(!q1.isEmpty()){
            TreeNode temp = (TreeNode)q1.poll();
            list.add(temp.val);
            if(temp.left != null) q2.add(temp.left);
            if(temp.right != null) q2.add(temp.right);
        }
        if(list.size() > 0)result.add(new ArrayList<Integer>(list));
        list.clear();
        while(!q2.isEmpty()){
            TreeNode temp = (TreeNode)q2.poll();
            list.add(temp.val);
            if(temp.left != null) q1.add(temp.left);
            if(temp.right != null) q1.add(temp.right);
        }
        if(list.size() > 0)result.add(new ArrayList<Integer>(list));
        list.clear();
    }
    return result;
}
2
Nitin Mendiratta

Essayez ceci en utilisant 2 files d'attente pour garder une trace des niveaux.

public static void printByLevel(Node root){
    LinkedList<Node> curLevel = new LinkedList<Node>();
    LinkedList<Node> nextLevel = curLevel;

    StringBuilder sb = new StringBuilder();
    curLevel.add(root);
    sb.append(root.data + "\n");

    while(nextLevel.size() > 0){
        nextLevel = new LinkedList<Node>();
        for (int i = 0; i < curLevel.size(); i++){
            Node cur = curLevel.get(i);
            if (cur.left != null) {
                nextLevel.add(cur.left);
                sb.append(cur.left.data + " ");
            }
            if (cur.right != null) {
                nextLevel.add(cur.right);
                sb.append(cur.right.data + " ");
            }
        }
        if (nextLevel.size() > 0) {
            sb.append("\n");
            curLevel = nextLevel;

        } 
    }
    System.out.println(sb.toString());
}
1
ywplee

J'aime beaucoup la simplicité du code de Anon; c'est élégant. Cependant, parfois un code élégant ne se traduit pas toujours par un code intuitivement facile à comprendre. Donc, voici ma tentative de montrer une approche similaire qui nécessite plus de place dans Log (n), mais que je devrais lire plus naturellement pour ceux qui sont les plus familiarisés avec la recherche de profondeur en premier (descendre le long d'un arbre)

L'extrait de code suivant définit les nœuds appartenant à un niveau particulier dans une liste et les range dans une liste contenant tous les niveaux de l'arborescence. D'où le List<List<BinaryNode<T>>> que vous verrez ci-dessous. Le reste devrait être assez explicite.

public static final <T extends Comparable<T>> void printTreeInLevelOrder(
        BinaryTree<T> tree) {
    BinaryNode<T> root = tree.getRoot();
    List<List<BinaryNode<T>>> levels = new ArrayList<List<BinaryNode<T>>>();
    addNodesToLevels(root, levels, 0);
    for(List<BinaryNode<T>> level: levels){
        for(BinaryNode<T> node: level){
            System.out.print(node+ " ");
        }
        System.out.println();
    }
}

private static final <T extends Comparable<T>> void addNodesToLevels(
        BinaryNode<T> node, List<List<BinaryNode<T>>> levels, int level) {
    if(null == node){
        return;
    }

    List<BinaryNode<T>> levelNodes;
    if(levels.size() == level){
        levelNodes = new ArrayList<BinaryNode<T>>();
        levels.add(level, levelNodes);
    }
    else{
        levelNodes = levels.get(level);
    }

    levelNodes.add(node);
    addNodesToLevels(node.getLeftChild(), levels, level+1);
    addNodesToLevels(node.getRightChild(), levels, level+1);
}
1
Salman Paracha
public class PrintATreeLevelByLevel {
public static class Node{
    int data;
    public Node left;
    public Node right;

    public Node(int data){
        this.data = data;
        this.left = null;
        this.right = null;

    }
}

public void printATreeLevelByLevel(Node n){
    Queue<Node> queue =  new LinkedList<Node>();
    queue.add(n);
    int node = 1; //because at root
    int child = 0; //initialize it with 0 
    while(queue.size() != 0){
        Node n1 = queue.remove();
        node--;
        System.err.print(n1.data +" ");

        if(n1.left !=null){
            queue.add(n1.left);
            child ++;
        }
        if(n1.right != null){
            queue.add(n1.right);
            child ++;
        }
        if( node == 0){
            System.err.println();
            node = child ;
            child = 0;
        }

    }


}

public static void main(String[]args){
    PrintATreeLevelByLevel obj = new PrintATreeLevelByLevel();
    Node node1 = new Node(1);
    Node node2 = new Node(2);
    Node node3 = new Node(3);
    Node node4 = new Node(4);
    Node node5 = new Node(5);
    Node node6 = new Node(6);
    Node node7 = new Node(7);
    Node node8 = new Node(8);

    node4.left = node2;
    node4.right = node6;
    node2.left = node1;
//  node2.right = node3;
    node6.left = node5;
    node6.right = node7;
    node1.left = node8;
    obj.printATreeLevelByLevel(node4);
}

}

1
javaMan

La réponse est proche ... le seul problème que je pouvais voir avec cela est que si un arbre n'a pas de nœud dans une position particulière, vous devez définir ce pointeur sur null. Que se passe-t-il lorsque vous essayez de placer un pointeur nul dans la liste?

Voici quelque chose que j'ai fait pour une mission récente. Cela fonctionne parfaitement. Vous pouvez l'utiliser à partir de n'importe quelle racine.

  //Prints the tree in level order
  public void printTree(){
    printTree(root);
  }

 public void printTree(TreeNode tmpRoot){

    //If the first node isn't null....continue on
    if(tmpRoot != null){

        Queue<TreeNode> currentLevel = new LinkedList<TreeNode>(); //Queue that holds the nodes on the current level
        Queue<TreeNode> nextLevel = new LinkedList<TreeNode>();     //Queue the stores the nodes for the next level

        int treeHeight = height(tmpRoot);     //Stores the height of the current tree
        int levelTotal = 0;  //keeps track of the total levels printed so we don't  pass the height and print a billion "null"s

        //put the root on the currnt level's queue
        currentLevel.add(tmpRoot);

        //while there is still another level to print and we haven't gone past the tree's height
        while(!currentLevel.isEmpty()&& (levelTotal< treeHeight)){

            //Print the next node on the level, add its childen to the next level's queue, and dequeue the node...do this until the current level has been printed
            while(!currentLevel.isEmpty()){

                //Print the current value
                System.out.print(currentLevel.peek().getValue()+" ");

                //If there is a left pointer, put the node on the nextLevel's stack. If there is no ponter, add a node with a null value to the next level's stack
                tmpRoot = currentLevel.peek().getLeft();
                if(tmpRoot != null)
                    nextLevel.add(tmpRoot);
                else
                    nextLevel.add(new TreeNode(null));

                //If there is a right pointer, put the node on the nextLevel's stack. If there is no ponter, add a node with a null value to the next level's stack
                tmpRoot = currentLevel.remove().getRight();
                if(tmpRoot != null)
                    nextLevel.add(tmpRoot);
                else
                    nextLevel.add(new TreeNode(null));

            }//end while(!currentLevel.isEmpty())

            //populate the currentLevel queue with items from the next level
            while(!nextLevel.isEmpty()){
                currentLevel.add(nextLevel.remove());
            }

            //Print a blank line to show height
            System.out.println("");

            //flag that we are working on the next level
            levelTotal++;

        }//end while(!currentLevel.isEmpty())

    }//end if(tmpRoot != null)

}//end method printTree

public int height(){
    return height(getRoot());
}

public int height(TreeNode tmpRoot){

    if (tmpRoot == null)
        return 0;
    int leftHeight = height(tmpRoot.getLeft());
    int rightHeight = height(tmpRoot.getRight());

    if(leftHeight >= rightHeight)
        return leftHeight + 1;
    else
        return rightHeight + 1;
 }
1
Rob

L’implémentation suivante utilise 2 files d’attente. UtiliserListBlokcingQueueici mais toute file d'attente fonctionnerait 

import Java.util.concurrent.*;

public class Test5 {

    public class Tree {
        private String value;
        private Tree left;
        private Tree right;

        public Tree(String value) {
            this.value = value;
        }

        public void setLeft(Tree t) {
            this.left = t;
        }

        public void setRight(Tree t) {
            this.right = t;
        }

        public Tree getLeft() {
            return this.left;
        }

        public Tree getRight() {
            return this.right;
        }

        public String getValue() {
            return this.value;
        }
    }

    Tree tree = null;

    public void setTree(Tree t) {
        this.tree = t;
    }

    public void printTree() {
        LinkedBlockingQueue<Tree> q = new LinkedBlockingQueue<Tree>();
        q.add(this.tree);
        while (true) {
            LinkedBlockingQueue<Tree> subQueue = new LinkedBlockingQueue<Tree>();
            while (!q.isEmpty()) {
                Tree aTree = q.remove();
                System.out.print(aTree.getValue() + ", ");
                if (aTree.getLeft() != null) {
                    subQueue.add(aTree.getLeft());
                }
                if (aTree.getRight() != null) {
                    subQueue.add(aTree.getRight());
                }
            }
            System.out.println("");
            if (subQueue.isEmpty()) {
                return;
            } else {
                q = subQueue;
            }
        }
    }

    public void testPrint() {
        Tree a = new Tree("A");
        a.setLeft(new Tree("B"));
        a.setRight(new Tree("C"));
        a.getLeft().setLeft(new Tree("D"));
        a.getLeft().setRight(new Tree("E"));
        a.getRight().setLeft(new Tree("F"));
        a.getRight().setRight(new Tree("G"));
        setTree(a);
        printTree();
    }

    public static void main(String args[]) {
        Test5 test5 = new Test5();
        test5.testPrint();
    }
}
1
Gautam
        Queue<Node> queue = new LinkedList<>();
        queue.add(root);

        Node leftMost = null;
        while (!queue.isEmpty()) {
            Node node = queue.poll();

            if (leftMost == node) {
                System.out.println();
                leftMost = null;
            }

            System.out.print(node.getData() + " ");

            Node left = node.getLeft();
            if (left != null) {
                queue.add(left);
                if (leftMost == null) {
                    leftMost = left;
                }
            }

            Node right = node.getRight();
            if (right != null) {
                queue.add(right);

                if (leftMost == null) {
                    leftMost = right;
                }
            }
        }
0
iMobaio
public void printAllLevels(BNode node, int h){
    int i;
    for(i=1;i<=h;i++){
        printLevel(node,i);
        System.out.println();
    }
}

public void printLevel(BNode node, int level){
    if (node==null)
        return;
    if (level==1)
        System.out.print(node.value + " ");
        else if (level>1){
            printLevel(node.left, level-1);
            printLevel(node.right, level-1);
        }
}

public int height(BNode node) {
    if (node == null) {
        return 0;
    } else {
        return 1 + Math.max(height(node.left),
                height(node.right));
    }
}

Tout d'abord, je n'aime pas prendre le crédit pour cette solution. C'est une modification de la fonction de quelqu'un et je l'ai adaptée pour fournir la solution.

J'utilise 3 fonctions ici.

  1. Je calcule d'abord la hauteur de l'arbre.
  2. J'ai ensuite une fonction pour imprimer un niveau particulier de l'arbre.
  3. En utilisant la hauteur de l’arbre et la fonction pour imprimer le niveau d’un arbre, je traverse l’arbre, puis itère et imprime tous les niveaux de l’arbre en utilisant ma troisième fonction. 

J'espère que ça aide.

EDIT: La complexité temporelle de cette solution pour l’impression de tous les nœuds en ordre de parcours ne sera pas O (n). La raison en est que chaque fois que vous descendez d'un niveau, vous visiterez les mêmes nœuds encore et encore. 

Si vous recherchez une solution O(n), je pense qu’utiliser des files d’attente serait une meilleure option. 

0
Naveen

Implémentation Python

# Function to  print level order traversal of tree
def printLevelOrder(root):
    h = height(root)
    for i in range(1, h+1):
        printGivenLevel(root, i)


# Print nodes at a given level
def printGivenLevel(root , level):
    if root is None:
        return
    if level == 1:
        print "%d" %(root.data),
    Elif level > 1 :
        printGivenLevel(root.left , level-1)
        printGivenLevel(root.right , level-1)


""" Compute the height of a tree--the number of nodes
    along the longest path from the root node down to
    the farthest leaf node
"""
def height(node):
    if node is None:
        return 0
    else :
        # Compute the height of each subtree 
        lheight = height(node.left)
        rheight = height(node.right)

        #Use the larger one
        if lheight > rheight :
            return lheight+1
        else:
            return rheight+1
0
Aerin

Imprimer l'arborescence binaire en ordre de niveau avec une seule file d'attente:

public void printBFSWithQueue() {
    Java.util.LinkedList<Node> ll = new LinkedList<>();
    ll.addLast(root);
    ll.addLast(null);
    Node in = null;
    StringBuilder sb = new StringBuilder();
    while(!ll.isEmpty()) {
        if(ll.peekFirst() == null) {
            if(ll.size() == 1) {
                break;
            }
            ll.removeFirst();
            System.out.println(sb);
            sb = new StringBuilder();
            ll.addLast(null);
            continue;
        }
        in = ll.pollFirst();
        sb.append(in.v).append(" ");
        if(in.left != null) {
            ll.addLast(in.left);
        }
        if(in.right != null) {
            ll.addLast(in.right);
        }
    }
}
0
susmit shukla

Je pense que nous pouvons y parvenir en utilisant une file d'attente elle-même. Ceci est une implémentation Java utilisant une seule file d'attente. Basé sur BFS ...

public void BFSPrint()
{
    Queue<Node> q = new LinkedList<Node>();
    q.offer(root);
    BFSPrint(q);
}

private void BFSPrint(Queue<Node> q)
{
    if(q.isEmpty())
        return;
    int qLen = q.size(),i=0;
     /*limiting it to q size when it is passed, 
       this will make it print in next lines. if we use iterator instead, 
       we will again have same output as question, because iterator 
       will end only q empties*/
    while(i<qLen) 
        {
        Node current = q.remove();
        System.out.print(current.data+" ");
        if(current.left!=null)
            q.offer(current.left);
        if(current.right!=null)
            q.offer(current.right);
        i++;
    }
    System.out.println();
    BFSPrint(q);

}
0
Raja Krishnan

Le moyen le plus simple de le faire sans utiliser aucune information de niveau supposée implicitement se trouver dans chaque nœud. Il suffit d'ajouter un nœud «nul» après chaque niveau. recherchez ce noeud nul pour savoir quand imprimer une nouvelle ligne:

public class BST{
     private Node<T> head;
     BST(){}
     public void setHead(Node<T> val){head = val;}

     public static void printBinaryTreebyLevels(Node<T> head){
         if(head == null) return;
         Queue<Node<T>> q = new LinkedList<>();//assuming you have type inference (JDK 7)
         q.add(head);
         q.add(null);
         while(q.size() > 0){
              Node n = q.poll();
              if(n == null){
                   System.out.println();
                   q.add(null);
                   n = q.poll();
              }
              System.out.print(n.value+" ");
              if(n.left != null) q.add(n.left);
              if(n.right != null) q.add(n.right);
         }
     }
     public static void main(String[] args){
           BST b = new BST();
           c = buildListedList().getHead();//assume we have access to this for the sake of the example
           b.setHead(c);
           printBinaryTreeByLevels();
           return;
     }
}
class Node<T extends Number>{
     public Node left, right;
     public T value;
     Node(T val){value = val;}
}
0
ak_2050

Cela fonctionne pour moi. Passez une liste de tableaux avec rootnode lors de l'appel de printLevel. 

void printLevel(ArrayList<Node> n){
    ArrayList<Node> next = new ArrayList<Node>();       
    for (Node t: n) {
        System.out.print(t.value+" "); 
        if (t.left!= null)
            next.add(t.left);
        if (t.right!=null)
            next.add(t.right);
    }
    System.out.println();
    if (next.size()!=0)
        printLevel(next);
}
0
bruhhhhh

Une solution

J'ai écrit la solution directe ici. Si vous souhaitez une réponse détaillée, un code de démonstration et une explication, vous pouvez ignorer et consulter les autres en-têtes de la réponse.

public static <T> void printLevelOrder(TreeNode<T> root) {
    System.out.println("Tree;");
    System.out.println("*****");

    // null check
    if(root == null) {
        System.out.printf(" Empty\n");
        return;
    }

    MyQueue<TreeNode<T>> queue = new MyQueue<>();
    queue.enqueue(root);

    while(!queue.isEmpty()) {
        handleLevel(queue);
    }
}

// process each level
private static <T> void handleLevel(MyQueue<TreeNode<T>> queue) {
    int size = queue.size();

    for(int i = 0; i < size; i++) {
        TreeNode<T> temp = queue.dequeue();
        System.out.printf("%s ", temp.data);
        queue.enqueue(temp.left);
        queue.enqueue(temp.right);
    }

    System.out.printf("\n");
}

B - Explication

Afin d'imprimer une arborescence dans l'ordre des niveaux, vous devez traiter chaque niveau à l'aide d'une simple implémentation de file d'attente. Dans ma démo, j'ai écrit une classe de files d'attente très minimaliste et simple appelée MyQueue .

La méthode publique printLevelOrder prendra l'instance d'objet TreeNode<T> root en tant que paramètre représentant la racine de l'arborescence. La méthode privée handleLevel prend l'instance MyQueue en tant que paramètre.

À chaque niveau, la méthode handleLevel élimine la file d'attente autant que la taille de la file d'attente. La restriction de niveau est contrôlée car ce processus est exécuté uniquement avec la taille de la file d'attente qui correspond exactement aux éléments de ce niveau, puis place un nouveau caractère de ligne dans la sortie.

C - classe TreeNode

public class TreeNode<T> {

    T data;
    TreeNode<T> left;
    TreeNode<T> right;

    public TreeNode(T data) {
        this.data = data;;
    }

}

D - Classe MyQueue: une implémentation simple de file d'attente

public class MyQueue<T> {

    private static class Node<T> {

        T data;
        Node next;

        public Node(T data) {
            this(data, null);
        }

        public Node(T data, Node<T> next) {
            this.data = data;
            this.next = next;
        }

    }

    private Node head;
    private Node tail;
    private int size;

    public MyQueue() {
        head = null;
        tail = null;
    }

    public int size() {
        return size;
    }

    public void enqueue(T data) {
        if(data == null)
            return;

        if(head == null)
            head = tail = new Node(data);
        else {
            tail.next = new Node(data);
            tail = tail.next;
        }

        size++;
    }

    public T dequeue() {

        if(tail != null) {
            T temp = (T) head.data;
            head = head.next;

            size--;

            return temp;
        }

        return null;
    }

    public boolean isEmpty() {
        return size == 0;
    }

    public void printQueue() {
        System.out.println("Queue: ");
        if(head == null)
            return;
        else {
            Node<T> temp = head;
            while(temp != null) {
                System.out.printf("%s ", temp.data);
                temp = temp.next;
            }
        }
        System.out.printf("%n");
    }
}

E - DEMO: Arbre d'impression en ordre de niveau

public class LevelOrderPrintDemo {

    public static void main(String[] args) {
        // root level
        TreeNode<Integer> root = new TreeNode<>(1);

        // level 1
        root.left           = new TreeNode<>(2);
        root.right          = new TreeNode<>(3);

        // level 2
        root.left.left      = new TreeNode<>(4);

        root.right.left     = new TreeNode<>(5);
        root.right.right    = new TreeNode<>(6);

        /*
         *      1      root
         *     / \
         *    2   3    level-1
         *   /   / \
         *  4   5   6  level-2
         */

        printLevelOrder(root);
    }

    public static <T> void printLevelOrder(TreeNode<T> root) {
        System.out.println("Tree;");
        System.out.println("*****");

        // null check
        if(root == null) {
            System.out.printf(" Empty\n");
            return;
        }

        MyQueue<TreeNode<T>> queue = new MyQueue<>();
        queue.enqueue(root);

        while(!queue.isEmpty()) {
            handleLevel(queue);
        }
    }

    // process each level
    private static <T> void handleLevel(MyQueue<TreeNode<T>> queue) {
        int size = queue.size();

        for(int i = 0; i < size; i++) {
            TreeNode<T> temp = queue.dequeue();
            System.out.printf("%s ", temp.data);
            queue.enqueue(temp.left);
            queue.enqueue(temp.right);
        }

        System.out.printf("\n");
    }

}

F - Exemple de saisie

    1      // root
   / \
  2   3    // level-1
 /   / \
4   5   6  // level-2

G - Exemple de sortie

Tree;
*****
1 
2 3 
4 5 6 
0
Levent Divilioglu

les solutions principales n'impriment que les enfants de chaque nœud. Ceci est faux selon la description.

Nous avons besoin de tous les nœuds du même niveau réunis dans la même ligne.

1) Appliquer BFS

2) Stocker les hauteurs de nœuds dans une carte qui contiendra niveau - liste de nœuds.

3) Parcourez la carte et imprimez les résultats. 

Voir le code Java ci-dessous:

public void printByLevel(Node root){
    Queue<Node> q = new LinkedBlockingQueue<Node>();
    root.visited = true;
    root.height=1;
    q.add(root);
    //Node height - list of nodes with same level
    Map<Integer, List<Node>> buckets = new HashMap<Integer, List<Node>>();
    addToBuckets(buckets, root);
    while (!q.isEmpty()){
        Node r = q.poll();

        if (r.adjacent!=null)
        for (Node n : r.adjacent){
            if (!n.visited){
                n.height = r.height+1; //adjust new height
                addToBuckets(buckets, n);
                n.visited = true;
                q.add(n);
            }
        }
    }

    //iterate over buckets and print each list
    printMap(buckets);

}

//helper method that adds to Buckets list
private void addToBuckets(Map<Integer, List<Node>> buckets, Node n){
        List<Node> currlist = buckets.get(n.height);
    if (currlist==null)
    {
        List<Node> list = new ArrayList<Node>();
        list.add(n);
        buckets.put(n.height, list);
    }
    else{
        currlist.add(n);
    }

}

//prints the Map
private void printMap(Map<Integer, List<Node>> buckets){
    for (Entry<Integer, List<Node>> e : buckets.entrySet()){
        for (Node n : e.getValue()){
            System.out.print(n.value + " ");
        }
    System.out.println();
}
0
mvogiatzis
void printTreePerLevel(Node root)
    {
        Queue<Node> q= new LinkedList<Node>();
        q.add(root);
        int currentlevel=1;
        int nextlevel=0;
        List<Integer> values= new ArrayList<Integer>();
        while(!q.isEmpty())
        {
            Node node = q.remove();
            currentlevel--;
            values.add(node.value);
            if(node.left != null)
            {
                q.add(node.left);
                nextlevel++;
            }
            if(node.right != null)
            {
                q.add(node.right);
                nextlevel++;
            }
            if(currentlevel==0)
            {
                for(Integer i:values)
                {
                    System.out.print(i + ",");
                }
                System.out.println();
                values.clear();
                currentlevel=nextlevel;
                nextlevel=0;
            }


        }

    }
0
Deepti Dua