java遍歷樹(深度遍歷和廣度遍歷)

java遍歷樹
如現有以下一顆樹:A     B          B1               B11          B2               B22     C          C1               C11               C12          C2     D          D1               D11

第一種方式深度優先遍歷 (最終返回的一棵壓扁的樹,依次從上往下)使用Stack,由於stack是先進後出,故實現方式爲:
首先push一個初始節點到stack中,假定爲A,
循環這個stack,只要不爲空則循環不結束,從stack中pop出第一個元素,把次元素放到一個list中,作爲樹的返回結果顯示,獲取次元素的下一級子元素,如果有則把他們都push到stack中。
首先第一次進入循環的stack中只有A,把A元素從stack中pop出來後,第一個被放到list裏,然後獲取到A的一級子元素(BCD),把他們push到stack中,此時stack中有三個元素(BCD),進入第二次循環。
這次循環從stack中pop出第一個元素B(注:這裏的BCD獲取的先後順序符合先進後出原則)把B元素從stack中pop出來後,第一個被放到list裏,然後獲取到A的一級子元素(B1B2),把他們push到stack中,此時stack中有元素(B1B2CD),進入第三次循環。
這次循環從stack中pop出的應該是B1或者B2中的一個,後面和上訴的循環一致。
獲取的結果爲A B B1 B11 B2 B22 C C1 C11 C12 C2 D D1 D11
第二種方式廣度優先遍歷使用list,由於list是集合,集合是先進先出,故實現方式爲:
首先add一個初始節點到list中,假定爲A,循環這個list,只要不爲空,則循環不結束,從這個list中取出第一個元素即A放到result(假定也是一個list)中,並且remove這個元素。然後獲取到A的一級子元素(BCD),把他們放到list中,此時list中有三個元素(BCD),進入第二次循環。
這次循環從list中取出第一個元素即B然後放到result中,並且remove這個元素。把B的一級子元素(B1B2)放入result中,此時list中元素爲(CDB1B2),進入第三次循環。
這次循環和上兩次一樣,取出的第一個元素是C。
獲取的結果爲A B C D B1 B2 C1 C2 D1 B11 B22 C11 C12 D11

 

 代碼試例:

package com.order;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Stack;
public class MytreeOrder {
 private static List<String> allElement = new ArrayList<String>();
 public static void setElement() {
  allElement.add("A");
  allElement.add("A1");
  allElement.add("A2");
  allElement.add("A3");
  allElement.add("A4");
  allElement.add("A11");
  allElement.add("A21");
  allElement.add("A22");
  allElement.add("A41");
  allElement.add("A42");
  allElement.add("A111");
  allElement.add("A421");
 }
 
 public static void main(String[] args) {
  setElement();
  deepOrder("A");
  broadOrder("A");
 }
 // 深度遍歷
 public static void deepOrder(String oneElement) {
  
  if (allElement.contains(oneElement)) {
   Stack<String> s = new Stack<String>();
   s.push(oneElement);
   while (!s.isEmpty()) {
    String now = s.pop();
    StringBuffer t = getSpace(now);
    System.out.println(t.toString() + now);
    s.addAll(getChild("deep", now));
   }
  }
  
 }
 // 根據傳入的string元素來返回需要的空格
 private static StringBuffer getSpace(String now) {
  StringBuffer t = new StringBuffer("");
  for (int i = 0; i < now.length(); i++) {
   t.append(" ");
  }
  return t;
 }
 // 獲取子元素
 private static Collection<String> getChild(String mode, String oneElement) {
  List<String> childs = new ArrayList<String>();
  for (int i = 0; i < allElement.size(); i++) {
   if (allElement.get(i).toString().length() == oneElement.length() + 1
     && (allElement.get(i).toString().substring(0,
       oneElement.length()).equals(oneElement))) {
    if (mode.equals("deep")) {
     // 此處保證集合中最後一個元素是需要顯示在當前層級中第一個展示的子節點(因爲堆棧中是最後一個元素先出)
     if (childs != null
       && childs.size() != 0
       && Integer.valueOf(allElement.get(i).toString()
         .substring(1)) > Integer.valueOf(childs
         .get(0).toString().substring(1))) {
      childs.add(0, allElement.get(i));
     } else {
      childs.add(allElement.get(i));
     }
    } else {
     if (childs != null
       && childs.size() != 0
       && Integer.valueOf(allElement.get(i).toString()
         .substring(1)) < Integer.valueOf(childs
         .get(0).toString().substring(1))) {
      childs.add(0, allElement.get(i));
     } else {
      childs.add(allElement.get(i));
     }
    }
   }
  }
  return childs;
 }
 // 廣度遍歷
 private static void broadOrder(String oneElement) {
  if (allElement.contains(oneElement)) {
   List<String> l = new ArrayList<String>();
   l.add(oneElement);
   while (!l.isEmpty()) {
    String now = l.get(0);
    l.remove(0);
    StringBuffer t = getSpace(now);
    System.out.println(t.toString() + now);
    l.addAll(getChild("broad", now));
   }
  }
 }
}

 


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章