二叉树11

二叉树的顺序存储

//
// Created by W9067299 on 2023/10/10.
//

#include <iostream>//定义头文件
#include <stdlib.h>//定义头文件
#include <deque>//定义头文件
#include <vector>//定义头文件
#include <queue>//定义头文件
using namespace std;
const int MaxSize=1024;
typedef struct
{
    int data[MaxSize];	//	存储树结点的数组
    int BiTreeNum;			//	二叉树的结点个数

}SqBiTree;


class tree{
public:
    vector<int> data = vector<int>(MaxSize,0);
    int  BiTreeNum;			//	二叉树的结点个数


};

//初始化树
void initTree(tree &T){
    T.BiTreeNum=0;
}
//创建树
void createTree(tree &T,int n){
    int ch;
    cin>>ch;
    if(ch == 0){
        return;
    }
    else{
        T.data[n] = ch;
        T.BiTreeNum++;
        cout<<"输入左子树值:"<<endl;
        createTree(T, 2*n);
        cout<<"输入右子树值:"<<endl;
        createTree(T,(2*n+1));
    }

}


void PreOrder_Traverse(tree T, int n)
{
    if(T.data[n] == 0) {
        cout << "空" << " ";
        return;
    }
    else
    {
        cout<<T.data[n]<<" ";
        PreOrder_Traverse(T, 2*n);
        PreOrder_Traverse(T, (2*n+1));
    }
}

void InOrder_Traverse(tree T, int n)
{
    if(T.data[n] == 0) {
        cout << "空" << " ";
        return;
    }
    else
    {
        InOrder_Traverse(T, 2*n);
        cout<<T.data[n]<<" ";
        InOrder_Traverse(T, (2*n+1));
    }
}

void PostOrder_Traverse(tree  T, int n) {
    if(T.data[n] == 0) {
        cout << "空" << " ";
        return;
    }
    else {
        PostOrder_Traverse(T, 2 * n);
        PostOrder_Traverse(T, (2 * n + 1));
        cout<<T.data[n]<<" ";
    }
}

//层序遍历 借助到队列
void cegxu_Treverse(tree  T, int n) {
    queue<int> m;
    //根节点队
    m.push(T.data[n]);
    int j=n;
    while (m.size()!=0){
        int l=2*j;
        int r=2*j+1;
        if(T.data[l]!=0)
            m.push(T.data[l]);
        if(T.data[r]!=0)
            m.push(T.data[r]);
        cout<<m.front()<<" ";
        m.pop();
        j++;
    }
}
int main(){
    tree T;
    cout<<"输入根节点的值:"<<endl;
    initTree(T);
    createTree(T,1);
    cout<<"先序遍历为:"<<endl;
    PreOrder_Traverse(T,1);
    cout<<endl;
    cout<<"层序遍历为:"<<endl;
    cegxu_Treverse(T,1);
    return 0;
}

链式存储

//
// Created by W9067299 on 2023/7/24.
//
#include <unordered_map>
#include "iostream"
#include "cstring"
#include "vector"
using namespace std;

class treenode{
public:
    treenode(int i) : left(nullptr), right(nullptr){
        value=i;
    }
    treenode *left;
    treenode *right;
    int value;
};

class tree{
public:
    treenode *root;
    int count=0;
    //构件树 先构建根节点
    treenode* create(){
        treenode *node;
        int temp;
        cin>>temp;
        if (temp==0){
            node= nullptr;
        } else {
            count++;
            node= new treenode(0);
            node->value=temp;
            node->left = create();
            node->right = create();
        }
        return node;
    }
    //先序遍历
    void preorder(treenode *r){
        if(r!= nullptr){
            cout<<r->value<<" ";
            preorder(r->left);
            preorder(r->right);
        }
    }
    //根据先序和中序创建树
    treenode* picreate(vector<int> pre,vector<int> inord){
        /**
         * 建立哈希索引
         */
        for (int i = 0; i < pre.size(); ++i) {
            pre_hash[i]= pre[i];
        }
        for (int i = 0; i < inord.size(); ++i) {
            inord_hash[inord[i]]= i;
        }
        return build(0,inord.size()-1,0);
    }
    treenode* build(int left,int right,int root_index_pre){
        if(left>right)
            return nullptr;
        treenode* root=new treenode(pre_hash[root_index_pre]);
        int root_index_inorder=inord_hash[pre_hash[root_index_pre]];
        int left_nodes=root_index_inorder-left;
        root->left= build(left,root_index_inorder-1,root_index_pre+1);
        //三个参数 最后一个是 就是先序遍历 前 左 右  定位到去除当前节点和左子树的节点
        root->right= build(root_index_inorder+1,right,root_index_pre+left_nodes+1);
        return root;
    }
    //销毁
    void shanchu(treenode *r){
        if(r!= nullptr){
            preorder(r->left);
            preorder(r->right);
            delete r;
        }
    }
    unordered_map<int,int> pre_hash;
    unordered_map<int,int> inord_hash;

};

int main(){
    tree mytree;
    mytree.root=mytree.create();
    mytree.preorder(mytree.root);
//    mytree.shanchu(mytree.root);
    cout<<mytree.count;
//    mytree.root=mytree.picreate({1,2,3,4,6,5,7},{2,1,6,4,3,5,7});
//    mytree.preorder(mytree.root);
    return 0;
}

C++标准模板库函数STL
数组:vector
栈:stack
队列:queue
堆(优先队列):priority_queue
哈希表:unordered_set 键值哈希表:unordered_map
红黑树:set 键值红黑树:map
考研只需要掌握最高频的几个api就行,考研是考你算法基础的,不是考你怎么炫技api的,Java的api过于炫技也许就是它从考研官方语言中被剔除的原因,扎实的基本功虽然朴素且低调,反而却是最实用和华丽的,
好人做到底,送佛送到西,直接给大家把408考试需要掌握C或者C++的API总结出来。
结构体
// C
typedef struct {                    
    int x; 
    int y;                     
}Point;

typedef struct point{  // point为标识                 
    int x; 
    int y;                     
}Point;  // Point为对象类型

// C++
struct Point {
    int x, y;
    Point(int _x, int _y): x(_x), y(_y) {}
};
数组:
#include <string.h> // 导入头文件
#include <iostream> // 导入头文件
#include <vector> // 导入头文件
#include <stdlib.h> // 导入头文件
using namespace std; // 声明命名空间
const int m = 50;
const int n = 100;
int main(){
    //
    int a[n]; //创建大小为n的数组, 下标范围[0,n-1]
    memset(a, 0, sizeof(a)); // 初始化所有元素为0
    a[5] = 1; //修改下标为5的元素值为1
    // 二维数组
    int g[m][n]; //创建大小为m*n的数组, m行n列,行下标范围[0,m-1],列下标范围[0,n-1],可用于创建邻接矩阵
    memset(g, 0, sizeof(g)); // 初始化所有元素为0
    g[5][4] = 1; //修改下标5行下标4列的元素值为1,邻接矩阵中结点0和结点1之间存在一条有向边,或者结点0和结点1之间有向边长度1
    //简单使用vector
    vector<int> c(7);
    c[5]=1;
    c.push_back(2);
    //初始化一个特殊的数组
    vector<int>  v3(5,111);//构造一个空间大小为5,并且元素为5个(每个元素初始值为111)的vector
    vector<int>  v4(v3);//拷贝构造vector
    //一维的遍历 记住这一个就行
    for (int i = 0; i < v3.size(); ++i) {
        cout<<v3[i]<<" ";
    }
    //二维数组
    vector<vector<int>> nums(m ,vector<int>(n,1)); //m*n的二维vector,所有元素为0 如果后面只填了vector<int> (n)默认全部值为0
    //不可以使用memset
    
    //二维的遍历
    for(int i = 0; i < nums.size(); i++){
        for(int j = 0; j < nums[0].size(); j++){
            cout<<nums[i][j]<<" ";
        }
    }
    return 0;
 }
 

重点  类中初始化为
class tree{
public:
    vector<int> data = vector<int>(MaxSize,0);
    int  BiTreeNum;       // 二叉树的结点个数
};
栈:
#include <stack> // 导入头文件
using namespace std; // 声明命名空间

stack<int> s; // 初始化一个空栈
s.push(1); // 入栈,向栈顶增加元素1
s.top(); // 返回当前栈顶元素值,注意在栈不为空的情况下进行
s.pop(); // 出栈,栈顶元素出栈,注意在栈不为空的情况下进行
s.empty(); // 返回当前栈是否为空
s.size(); // 返回当前栈的元素个数
队列:
#include <queue> // 导入头文件
using namespace std; // 声明命名空间

queue<int> q; // 初始化一个队列
q.push(1); // 入队,向队尾增加元素1
q.front(); // 返回当前队列头元素值,注意在队列不为空的情况下进行
q.pop(); // 出队,弹出队头元素
q.empty(); // 返回当前队列是否为空
q.size(); // 返回当前队列的元素个数
堆(优先队列):priority_queue
#include <queue> // 导入头文件
using namespace std; // 声明命名空间

// 大顶堆
priority_queue<int> max_heap; 
priority_queue<int, vector<int>, less<int>> max_heap; 
// 小顶堆
priority_queue<int, vector<int>, greater<int>> min_heap; 

priority_queue<int> pq; // 初始化一个大顶堆
pq.push(1); // 向堆中插入一个元素 
pq.top(); // 返回堆顶元素值
pq.pop(); // 移除堆顶元素
pq.empty(); // 返回当前堆是否为空
pq.size(); // 返回当前堆中元素个数
哈希表:unordered_set
#include <unordered_set> // 导入头文件
using namespace std; // 声明命名空间

unordered_set<int> s; // 创建哈希表
s.insert(1); // 向哈希表中插入元素1
s.count(1); // 返回哈希表中是否存在元素1
s.size(); // 返回哈希表中元素个数
键值哈希表:unordered_map
#include <unordered_map> // 导入头文件
using namespace std; // 声明命名空间

unordered_map<int, int> mp; // 创建键值哈希表,第一个类型为key类型,第二个类型为value类型
mp[1] = 10; // 设定key为1的value为10
mp[1]++; // 设定key为1的value增加1
mp.count(1); // 返回键值哈希表中是否存在键值为1的元素
mp[1]; // 获取key为1的value,如果不存在,会自动创建key为1,value为默认0
mp.size(); // 返回哈希表中元素个数
注:键key为char或者26个字母的哈希表建议用数组代替:
// C
int cnt[128]; // key为char类型
memset(cnt, 0, sizeof(cnt)); // 初始化所有key的value为0
cnt[c] = 1; // key为c的value设为1
cnt[c]; // 返回key为c的value

int cnt[26]; // key为26个字母
memset(cnt, 0, sizeof(cnt)); // 初始化所有key的value为0
cnt[c - 'a'] = 1; // key为小写字母c的value设为1
cnt[c - 'a']; // 返回key为小写字母c的value

// C++
vector<int>cnt(128); // key为char类型
cnt[c] = 1; // key为c的value设为1
cnt[c]; // 返回key为c的value

vector<int>cnt(26); // key为26个字母
cnt[c - 'a'] = 1; // key为小写字母c的value设为1
cnt[c - 'a']; // 返回key为小写字母c的value
红黑树:set
#include <set> // 导入头文件
using namespace std; // 声明命名空间

set<int> s; // 创建红黑树
s.insert(1); // 向红黑树中插入元素1
s.count(1); // 返回红黑树中是否存在元素1
s.size(); // 返回红黑树中元素个数
键值红黑树:map
#include <map> // 导入头文件
using namespace std; // 声明命名空间

map<int, int> mp; // 创建键值红黑树,第一个类型为key类型,第二个类型为value类型
mp[1] = 10; // 设定key为1的value为10
mp[1]++; // 设定key为1的value增加1
mp.count(1); // 返回键值红黑树中是否存在键值为1的元素
mp[1]; // 获取key为1的value,如果不存在,会自动创建key为1,value为默认0
mp.size(); // 返回红黑树中元素个数
数学
这个理论上不推荐使用,但是我列出的几个属于最简单的了,理论上不会扣分。
保险起见可以使用 if else 或者三目运算符。
#include <algorithm> // 导入头文件
using namespace std; // 声明命名空间

max(x, y); // 返回x和y中的最大值,注意x和y类型要相同
min(x, y); // 返回x和y中的最小值,注意x和y类型要相同
abs(x); // 返回x的绝对值
内存分配与回收
这个属于为了严谨,不写理论上不扣分。
// C
#include <stdlib.h> // 注:和C++混编时写为 #include <cstdlib>
typename *p=(typename*)malloc(sizeof(typename));
free(p);

// C++
#include <iostream>
using namespace std;
typename *p=new typename;
delete(p);

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值