王道数据结构4.3.3大题

1、高度=结点数

2、只有一个根结点

3、后序遍历的非递归算法

void posorder(BTNode *bt){
    if(bt!=NULL){
        BTNode *Stack1[maxSize];int top1=-1;
        BTNode *Stack2[maxSize];int top2=-1;
        Stack1[++top1]=bt;
        BTNode *p=NULL;
        while(top1!=-1){
            p=Stack1[top1--];
            Stack2[++top2]=p;
            if(p->lchild!=NULL){
                Stack1[++top1]=p->lchild;
            }
            if(p->rchild!=NULL){
                Stack1[++top1]=p->rchild;
            }
        }
        while(top2!=-1){
            p=Stack2[top2--];
            visit(p);
        }
    }
}

4、二叉树自下而上、从左到右的层次遍历

void levelorder(BTNode *bt){
    if(bt!=NULL){
        BTNode *que[maxSize],*Stack[maxSize];
        int front=-1,rear=-1,top=-1;
        que[++rear]=bt;
        BTNode *p;
        while(front!=rear){
            p=que[++front];
            Stack[++top]=p;
            if(p->lchild!=NULL){
                que[++rear]=p->lchild;
            }
            if(p->rchild!=NULL){
                que[++rear]=p->rchild;
            }
        }
        while(top!=-1){
            p=Stack[top--];
            visit(p);
        }
    }
}

5、非递归算法求二叉树高度

int levelorder(BTNode *bt){
    if(bt!=NULL){
        BTNode *que[maxSize];
        int front=-1,rear=-1;
        int last=0,level=0;
        que[++rear]=bt;
        BTNode *p;
        while(front!=rear){
            p=que[++front];
            if(p->lchild!=NULL){
                que[++rear]=p->lchild;
            }
            if(p->rchild!=NULL){
                que[++rear]=p->rchild;
            }
            if(front==last){
                level++;
                last=rear;
            }
        }
        return level;
    }else{
        return 0;
    }
}

6、已知先序遍历和中序遍历,求二叉链表

BTNode *Create(char pre[],char in[],int l1,int r1,int l2,int r2){
    if(l1>r1) return NULL;
    BTNode *s=(BTNode *)malloc(sizeof(BTNode));
    s->lchild=NULL;s->rchild=NULL;
    for(int i=l2;i<=r2;i++){
        if(in[i]==pre[l1]) break;
    }
    s->data=in[i];
    s->lchild=Create(pre,in,l1,l1+i-l2,l2,i-1);
    s->rchild=Create(pre,in,l1+i-l2+1,r1,i+1,r2);
    return s;
}

7、判断二叉树是否为完全二叉树

bool isComplete(BTNode *bt){
    if(bt!=NULL){
        BTNode *que[maxSize];
        int front=-1,rear=-1,flag=0;
        que[++rear]=bt;
        BTNode *p;
        while(front!=rear){
            p=que[++front];
            if(p!=NULL){
                que[++rear]=p->lchild;
                que[++rear]=p->rchild;
            }
            else if(p==NULL&&flag==0) flag=1;
            else if(p!=NULL&&flag==1) return 0;
        }
        return 1;
    }else return 1;
}

8、求二叉树中度为2的结点个数(略)

9、把二叉树中所有结点的左右子树交换

//后序交换
void exchange(BTNode *bt){
    if(bt!=NULL){
        exchange(bt->lchild);
        exchange(bt->rchild);
        BTNode *temp;
        temp=bt->lchild;
        bt->lchild=bt->rchild;
        bt->rchild=temp;
    }
}
//层序交换
void exchange(BTNode *bt){
    if(bt!=NULL){
        BTNode *que[maxSize];
        int front=-1,rear=-1;
        que[++rear]=bt;
        BTNode *p,*temp;
        while(front!=rear){
            p=que[++front];
            temp=p->lchild;
            p->lchild=p->rchild;
            p->rchild=temp;
            if(p->lchild!=NULL)
                que[++rear]=p->lchild;
            if(p->rchild!=NULL)
                que[++rear]=p->rchild;
        }
    }
}

10、求先序遍历中第k个结点的值

int count=0;char ch;
ElemType preorder(BTNode *bt,int k){
    if(bt==NULL) return '#'
    count++;
    if(count==k) return bt->data;
    ch=preorder(bt->lchild,k);
    if(ch!='#') return ch;
    return preorder(bt->rchild,k);
}

11、删除二叉树中值为x的结点以及其子树

void delete_x(BTNode *bt){
    if(bt!=NULL){
        if(bt->data==x){
            deleteAllTree(bt);
            return;
        }
        BTNode *que[maxSize];
        int front=rear=-1;
        que[++rear]=bt;
        BTNode *p,*r;
        while(front!=rear){
            p=que[++front];
            if(p->lchild->data==x)
                deleteAllTree(p->lchild);
            else
                que[++rear]=p->lchild;
            if(p->rchild->data==x)
                deleteAllTree(p->rchild);
            else 
                que[++rear]=p->rchild;
        }
    }
}

12、打印值为x的结点的所有祖先结点

//添加了parent指针的结构体
typedef struct BTNode{
    char data[];
    struct BTNode *lchild,*rchild,*parent;
}BTNode;
//给一棵树的parent指针赋值
void triBtree(BTNode *p,BTNode *q){
    if(p!=NULL){
        p->parent=q;
        q=p;
        triBtree(q->lchild,q);
        triBtree(q->rchild,q);
    }
}
//打印x到根结点的路径
void printX(BTNode *bt, char x){
    if(bt!=NULL){
        if(bt->data==x){
            while(bt!=NULL)
                cout<<bt->data<<endl;
            return;
        }else{
            printX(bt->lchild,x);
            printX(bt->rchild,x);
        }
    }
}

13、找出二叉树中结点p和结点q的最近公共祖先结点r

typedef struct BTNode{
    char INFO;
    struct BTNode *LLINK,*RLINK;
}BTNode;
int find=m=0;
void path(BTNode *bt,BTNode *t,BTNode *&arr){
    if(bt!=NULL){
        if(bt==t&&find==0) 
            find=1;
        else if(find==1) 
            arr[m++]=bt;
        if(find!=1) 
            path(bt->LLINK,t,que);
        if(find!=1) 
            path(bt->RLINK,t,que);
    }
}
BTNode* find_common(BTNode *bt,BTNode *p,BTNode *q){
    BTNode *arr1[maxSize],*arr2[maxSize];
    path(bt,p,arr1);
    find=m=0;
    path(bt,q,arr2);
    int i=0;
    while(arr1[i]!=NULL&&arr2[i]!=NULL){
        if(arr1[i]==arr2[i])
            return arr1[i];
        i++;
    }
}

14、与用层次遍历求高度类似。

int width(BTNode *bt){
    if(bt!=NULL){
        BTNode *que[maxSize],*p;
        int front=rear=-1,last=0,sum=0,max_sum=0;
        que[++rear]=bt;
        while(front!=rear){
            p=que[++front];
            sum++;
            if(p->lchild!=NULL)
                que[++rear]=p->lchild;
            if(p->rchild!=NULL)
                que[++rear]=p->rchild;
            if(front==last){
                last=rear;
                if(sum>max_sum) max_sum=sum;
                sum=0;
            }
        }
        return max_sum;
    }else{
        return 0;
    }
}

15、类似6题

void change(char pre[],int l1,int r1,char &post[],int l2,int r2){
    int half;
    if(r1>=l1){
        post[r2]=pre[l1];
        half=(r1-l1)/2;
        change(pre,l1+1,l1+half,post,l2,l2+half-1);
        change(pre,l1+half+1,r1,post,l2+half,r2-1);
    }
}

16、将二叉树的叶结点连接成链表

int flag=0;
BTNode *head,*p;
BTNode* preorder(BTNode *bt){
    if(bt!=NULL){
        visit(bt);
        if(bt->lchild==NULL&&bt->rchild==NULL&&flag==0){
            flag=1;head=bt;p=bt;p->rchild=NULL;
        }else if(bt->lchild==NULL&&bt->rchild==NULL&&flag==1){
            p->rchild=bt;p=bt;p->rchild=NULL;
        }
        preorder(bt->lchild);
        preorder(bt->rchild);
    }
    return head;
}

17、判断两树是否相等

int resemble(BTNode *p,BTNode *q){
    int leftS,rightS;
    if(p==NULL&&q==NULL){   //都是空二叉树
        return 1;
    }else if(p=NULL||q==NULL){ //一空一非空
        return 0;
    }else{
        leftS=resemble(p->lchild,q->lchild);
        rightS=resemble(p->rchild,q->rchild);
        return leftS&&rightS;
    }
}

18、写出在中序线索二叉树中查找指定结点在后序的前驱结点的算法

这题只要搞清楚,后序线索二叉树中,结点 p 的前驱有以下四种情况:(1)若p有右孩子,则p的前驱是右孩子(2)若p没有右孩子,而有左孩子,则p的前驱是左孩子(3)若p没有左、右孩子,则p的前驱是父节点的左孩子,若父节点没有左孩子,找爷爷结点的左孩子,再没有则再往上...如果到根结点也没有,那么p的前驱就是空。

TBTNode* InPostPre(TBTNode *t,TBTNode *p){
    if(p->rtag==0)
        return p->rchild;
    if(p->ltag==0)
        return p->lchild;
    while(p&&p->ltag==1)//没有左孩子就一直往上找,直到根结点或有左孩子
        p=p->lchild;
    if(p) 
        return p->lchild;
    return NULL;
}

19、求二叉树的带权路径长度

//结构体
typedef struct BTNode{
    int weight;
    struct BTNode *right,*left;
}BTNode;
//调用方法
int WPL(BTNode *root){
    return wpl_pre(root,0);
}
//求WPL算法
int preorder(BTNode *root,int level){
    static int wpl=0;
    level++;
    if(root->left==NULL&&root->right==NULL)
        wpl+=level*root->weight;
    if(root->left!=NULL)
        preorder(root->right);
    if(root->right!=NULL)
        preorder(root->left);
    return wpl;
}

20、将二叉树转化为中缀表达式

void preorder(BTNode *bt, int deep){
    if(bt!=NULL){
        if(deep>1 && bt->right!=NULL || bt->left!=NULL){
            cout<<'('<<endl;
        }
        preorder(bt->left,deep+1);
        cout<<bt->data<<endl;
        preorder(bt->right,deep+1);
        if(deep>1 && bt->right!=NULL || bt->left!=NULL){
            cout<<')'<<endl;
        }
    }
}

 

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值