算法基础——二叉树

一、⼆叉树的概念

1. 二叉树的定义

注意:⼆叉树结点的两个孩⼦,⼀个被称为左孩⼦,⼀个被称为右孩⼦。其顺序是固定的,就像⼈ 的左⼿和右⼿,不能颠倒混淆。

2. 特殊的⼆叉树

(1)满⼆叉树

(2)完全⼆叉树

对⼀棵树有 个结点的⼆叉树按层序编号,所有的结点的编号从 样深度的满⼆叉树的编号为从 1 ∼n 1 ∼n 。如果这棵树所有结点和同 比特就业课 的结点位置相同,则这棵⼆叉树为完全⼆叉树。

注意:要从后往前依次删除!!!

二、⼆叉树的存储

1. 顺序存储

2. 链式存储


案例:

题⽬描述: 有⼀个 n (n ≤ 10^6 ) 个结点的⼆叉树。给出每个结点的两个⼦结点编号(均不超过n ),建⽴⼀棵⼆叉树(根节点的编号为1 ),如果是叶⼦结点,则输⼊ 0 0。

输⼊描述:
第⼀⾏⼀个整数 n ,表⽰结点数。
之后 n ⾏,第 i ⾏两个整数 lr ,分别表⽰结点 i 的左右⼦结点编号。若 l = 0 则表⽰⽆左⼦结点, r = 0 同理。

代码实现:

cpp 复制代码
#include <iostream>

using namespace std;

const int N = 1e6 + 10;

int n;
int l[N], r[N];

int main()
{   
    cin >> n;
    // 存二叉树
    for(int i = 1; i <= n; i++)
    {
        cin >> l[i] >> r[i];
    }


    return 0;
}

三、 ⼆叉树的遍历

1. 深度优先遍历

案例:

题⽬描述:
有⼀个 n (n ≤ 10^6 ) 个结点的⼆叉树。给出每个结点的两个⼦结点编号(均不超过 n ),建⽴⼀棵⼆叉树(根节点的编号为1 ),如果是叶⼦结点,则输⼊ 0 0。
输⼊描述:

第⼀⾏⼀个整数 n ,表⽰结点数。之后 n ⾏,第 i ⾏两个整数 lr ,分别表⽰结点 i 的左右⼦结点编号。若 l = 0m则表⽰⽆左⼦结点, r = 0 同理。

cpp 复制代码
测试⼀:
 4
 0 2
 3 4
 0 0
 0 0
测试⼆:
 2
 2 0
 0 0
测试三:
 3
 2 3
 0 0
 0 0
测试四:
 7
 2 3
 0 4
 5 6
 0 0
 0 0
 7 0
 0 0

代码实现:

cpp 复制代码
#include <iostream>

using namespace std;

const int N = 1e6 + 10;

int n;
int l[N], r[N]; // 存树

// 先序遍历
void dfs1(int u)
{
    cout << u << " ";
    if(l[u]) dfs1(l[u]);
    if(r[u]) dfs1(r[u]);
}

// 中序遍历
void dfs2(int u)
{
    if(l[u]) dfs2(l[u]);
    cout << u << " ";
    if(r[u]) dfs2(r[u]);
}

// 后序遍历
void dfs3(int u)
{
    if(l[u]) dfs3(l[u]);
    if(r[u]) dfs3(r[u]);
    cout << u << " ";
}

int main()
{
    cin >> n;
    for(int i = 1; i <= n; i++)
    {
        cin >> l[i] >> r[i];
    }

    dfs1(1); // 先序遍历
    cout << endl;

    dfs2(1); // 中序遍历
    cout << endl;

    dfs3(1); // 后序遍历
    cout << endl;

    return 0;
}

2. 宽度优先遍历

这个就和常规的树的遍历⽅式⼀样,直接⽤队列帮助层序遍历即可。

cpp 复制代码
#include <iostream>
#include <queue>

using namespace std;

const int N = 1e6 + 10;

int n;
int l[N], r[N];

void bfs()
{
    queue<int> q;
    q.push(1);

    while(q.size())
    {
        int u = q.front(); q.pop();
        cout << u << " ";

        if(l[u]) q.push(l[u]);
        if(r[u]) q.push(r[u]);
    }
}

int main()
{
    cin >> n;
    for(int i = 1; i <= n; i++)
    {
        cin >> l[i] >> r[i];
    }

    bfs();


    return 0;
}
相关推荐
浅念-40 分钟前
刷穿LeetCode:BFS 解决 Flood Fill 算法
数据结构·c++·算法·leetcode·职场和发展·bfs·宽度优先
做cv的小昊1 小时前
【TJU】研究生应用统计学课程笔记(8)——第四章 线性模型(4.1 一元线性回归分析)
笔记·线性代数·算法·数学建模·回归·线性回归·概率论
贾斯汀玛尔斯2 小时前
每天学一个算法--倒排索引(Inverted Index)
算法·inverted-index
楼田莉子2 小时前
Linux网络:NAT_代理
linux·运维·服务器·开发语言·c++·后端
小e说说2 小时前
打破偏科困境:这些学习软件助孩子重燃学习热情
算法
南境十里·墨染春水2 小时前
C++日志 2——实现单线程日志系统
java·jvm·c++
zh_xuan2 小时前
api测试工具添加历史记录功能
c++·libcurl·duilib
月昤昽3 小时前
autoCAD二次开发 4.正多边形与collection区分
算法·c#·二次开发·autocad二次开发
休息一下接着来3 小时前
C++ 固定容量环形队列实现
c++·算法
im_AMBER3 小时前
手撕hot100之矩阵!看完这篇就AC~
javascript·数据结构·线性代数·算法·leetcode·矩阵