1.java实现非递归层序遍历
public class Code03_UnRecursiveTraversalBT {
public static class Node {
public int value;
public Node left;
public Node right;
public Node(int v) {
value = v;
}
}
public static void pre(Node head) {
System.out.print("pre-order: ");
if (head != null) {
Stack<Node> stack = new Stack<Node>();
stack.add(head);
while (!stack.isEmpty()) {
head = stack.pop();
System.out.print(head.value + " ");
if (head.right != null) {
stack.push(head.right);
}
if (head.left != null) {
stack.push(head.left);
}
}
}
System.out.println();
}
public static void in(Node cur) {
System.out.print("in-order: ");
if (cur != null) {
Stack<Node> stack = new Stack<Node>();
while (!stack.isEmpty() || cur != null) {
if (cur != null) {
stack.push(cur);
cur = cur.left;
} else {
cur = stack.pop();
System.out.print(cur.value + " ");
cur = cur.right;
}
}
}
System.out.println();
}
public static void pos1(Node head) {
System.out.print("pos-order: ");
if (head != null) {
Stack<Node> s1 = new Stack<Node>();
Stack<Node> s2 = new Stack<Node>();
s1.push(head);
while (!s1.isEmpty()) {
head = s1.pop(); // 头 右 左
s2.push(head);
if (head.left != null) {
s1.push(head.left);
}
if (head.right != null) {
s1.push(head.right);
}
}
// 左 右 头
while (!s2.isEmpty()) {
System.out.print(s2.pop().value + " ");
}
}
System.out.println();
}
public static void pos2(Node h) {
System.out.print("pos-order: ");
if (h != null) {
Stack<Node> stack = new Stack<Node>();
stack.push(h);
Node c = null;
while (!stack.isEmpty()) {
c = stack.peek();
if (c.left != null && h != c.left && h != c.right) {
stack.push(c.left);
} else if (c.right != null && h != c.right) {
stack.push(c.right);
} else {
System.out.print(stack.pop().value + " ");
h = c;
}
}
}
System.out.println();
}
public static void main(String[] args) {
Node head = new Node(1);
head.left = new Node(2);
head.right = new Node(3);
head.left.left = new Node(4);
head.left.right = new Node(5);
head.right.left = new Node(6);
head.right.right = new Node(7);
pre(head);
System.out.println("========");
in(head);
System.out.println("========");
pos1(head);
System.out.println("========");
pos2(head);
System.out.println("========");
}
}
2.java实现树的最大宽度
public class Code05_TreeMaxWidth {
public static class Node {
public int value;
public Node left;
public Node right;
public Node(int data) {
this.value = data;
}
}
public static int maxWidthUseMap(Node head) {
if (head == null) {
return 0;
}
Queue<Node> queue = new LinkedList<>();
queue.add(head);
// key 在 哪一层,value
HashMap<Node, Integer> levelMap = new HashMap<>();
levelMap.put(head, 1);
int curLevel = 1; // 当前你正在统计哪一层的宽度
int curLevelNodes = 0; // 当前层curLevel层,宽度目前是多少
int max = 0;
while (!queue.isEmpty()) {
Node cur = queue.poll();
int curNodeLevel = levelMap.get(cur);
if (cur.left != null) {
levelMap.put(cur.left, curNodeLevel + 1);
queue.add(cur.left);
}
if (cur.right != null) {
levelMap.put(cur.right, curNodeLevel + 1);
queue.add(cur.right);
}
if (curNodeLevel == curLevel) {
curLevelNodes++;
} else {
max = Math.max(max, curLevelNodes);
curLevel++;
curLevelNodes = 1;
}
}
max = Math.max(max, curLevelNodes);
return max;
}
public static int maxWidthNoMap(Node head) {
if (head == null) {
return 0;
}
Queue<Node> queue = new LinkedList<>();
queue.add(head);
Node curEnd = head; // 当前层,最右节点是谁
Node nextEnd = null; // 下一层,最右节点是谁
int max = 0;
int curLevelNodes = 0; // 当前层的节点数
while (!queue.isEmpty()) {
Node cur = queue.poll();
if (cur.left != null) {
queue.add(cur.left);
nextEnd = cur.left;
}
if (cur.right != null) {
queue.add(cur.right);
nextEnd = cur.right;
}
curLevelNodes++;
if (cur == curEnd) {
max = Math.max(max, curLevelNodes);
curLevelNodes = 0;
curEnd = nextEnd;
}
}
return max;
}
// for test
public static Node generateRandomBST(int maxLevel, int maxValue) {
return generate(1, maxLevel, maxValue);
}
// for test
public static Node generate(int level, int maxLevel, int maxValue) {
if (level > maxLevel || Math.random() < 0.5) {
return null;
}
Node head = new Node((int) (Math.random() * maxValue));
head.left = generate(level + 1, maxLevel, maxValue);
head.right = generate(level + 1, maxLevel, maxValue);
return head;
}
public static void main(String[] args) {
int maxLevel = 10;
int maxValue = 100;
int testTimes = 1000000;
for (int i = 0; i < testTimes; i++) {
Node head = generateRandomBST(maxLevel, maxValue);
if (maxWidthUseMap(head) != maxWidthNoMap(head)) {
System.out.println("Oops!");
}
}
System.out.println("finish!");
}
}
C实现基于递归遍历和高度
用到的库基本库<stdio.h>、需要分配地址空间的库<malloc.h>
//创建二叉树
int createBTNode(BTNode * &BT,char *str,int n)
//销毁二叉树
void destroyBTNode(BTNode * &BT)
//查找结点存在
BTNode *findBTNode(BTNode * &BT,char ch)
//求高度
int BTHeight(BTNode * &BT)
//输出二叉树
void displayBTNode(BTNode * &BT)
//先序遍历
void preOrder(BTNode * &BT)
//中序遍历
void inOrder(BTNode * &BT)
//后序遍历
void postOrder(BTNode * &BT)
#include<stdio.h>
#include<malloc.h>
typedef struct node{
struct node *lchild; //指向左孩子节点
char data; //数据元素
struct node *rchild; //指向右孩子节点
}BTNode;
int createBTNode(BTNode * &BT,char *str,int n){
printf("%d ",n);
char ch=str[n]; //把第 n 个字符赋给ch,方便后面判断
printf("%c \n",ch);
n=n+1;
if(ch!='\0'){ //如果 ch 不等于结束符就继续创建,否则就结束
if( ch=='#'){ //以 # 号代表 NULL,下面没有了
BT = NULL;
}
else{
BT = new BTNode; //新建一个二叉链
BT->data=ch; //把字符存入二叉链
n=createBTNode(BT->lchild,str,n); //左递归创建
n=createBTNode(BT->rchild,str,n); //右递归创建
}
}
return n; //返回 n,记录字符串使用到哪里了
}
void destroyBTNode(BTNode * &BT){
if(BT!=NULL){
destroyBTNode(BT->lchild); //左递归释放内存
destroyBTNode(BT->rchild); //右递归释放内存
/*
free()释放的是指针指向的内存!注意!释放的是内存,不是指针!这点非常非常重要!
指针是一个变量,只有程序结束时才被销毁。释放内存空间。
原来指向这块空间的指针还是存在!只不过现在指针指向的内容是未定义的。
因此,释放内存后把指针指向NULL,防止指针在后面不小心又被引用了。非常重要啊这一点!
*/
free(BT);
BT=NULL;
}
}
BTNode *findBTNode(BTNode * &BT,char ch){
if(BT==NULL){ //空,返回为空 NULL
return NULL;
}
else if(BT->data==ch){ //存在,提示存在并返回数据
printf("存在该节点:%c",ch);
return BT;
}
else{
BTNode *p; //定义一个链表指针
p=findBTNode(BT->lchild,ch); //递归查询左子树
if(p!=NULL){
return p; //左子树已经找到
}
else{
return findBTNode(BT->rchild,ch); //递归查询右子树
}
}
}
int BTHeight(BTNode * &BT){
int lchildh;
int rchildh;
int h;
if(BT==NULL){
return 0; //空树高度为0
}
else{
lchildh=BTHeight(BT->lchild); //求左子树的高度
rchildh=BTHeight(BT->rchild); //求右子树的高度
h=(lchildh>rchildh)?(lchildh+1):(rchildh+1); //比较左子树和右子树,高度高的再 +1(根节点) 就是树的高度
return h;
}
}
void displayBTNode(BTNode * &BT){
if(BT!=NULL){
printf("%c",BT->data);
if(BT->lchild!=NULL || BT->rchild!=NULL){
printf("(");
displayBTNode(BT->lchild);
printf(",");
displayBTNode(BT->rchild);
printf(")");
}
}
}
void displayBTNode1(BTNode * &BT){
if(BT!=NULL){
printf("%c",BT->data);
displayBTNode1(BT->lchild);
displayBTNode1(BT->rchild);
}
else{
printf("#");
}
}
void preOrder(BTNode * &BT){
if(BT!=NULL){ //判断不为空
printf("%c",BT->data); //访问根节点
preOrder(BT->lchild); //递归,先序遍历左子树
preOrder(BT->rchild); //递归,先序遍历右子树
}
}
void inOrder(BTNode * &BT){
if(BT!=NULL){
inOrder(BT->lchild);
printf("%c",BT->data);
inOrder(BT->rchild);
}
}
void postOrder(BTNode * &BT){
if(BT!=NULL){
postOrder(BT->lchild);
postOrder(BT->rchild);
printf("%c",BT->data);
}
}
int main(){
//例子:ABC###D##
BTNode *BT;
printf("输入字符串:");
char *str=(char *)malloc(sizeof(char) * 1024);
scanf("%s",str);
createBTNode(BT,str,0);
printf("二叉树建立成功\n");
destroyBTNode(BT);
if(BT==NULL){
printf("销毁成功\n");
}
// printf("请输入要查找的节点:");
// char c='E';
// printf("%c\n",c);
// if(findBTNode(BT,c)==NULL){
// printf("没有此节点");
// }
// printf("\n");
//
// int h=BTHeight(BT);
// printf("树的高度为:%d",h);
// printf("\n");
//
// printf("二叉树为:");
// displayBTNode(BT);
// printf("\n");
// printf("二叉树为:");
// displayBTNode1(BT);
// printf("\n");
//
// printf("先序遍历结果:");
// preOrder(BT);
// printf("\n");
//
// printf("中序遍历结果:");
// inOrder(BT);
// printf("\n");
//
// printf("后序遍历结果:");
// postOrder(BT);
// printf("\n");
return 0;
}