目录
二叉树的遍历
B3642 二叉树的遍历 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
完全二叉树的权值
0完全二叉树的权值 - 蓝桥云课 (lanqiao.cn)
美国血统 American Heritage
P1827 [USACO3.4] 美国血统 American Heritage - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
求先序排列
P1030 [NOIP2001 普及组] 求先序排列 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
二叉树的遍历
B3642 二叉树的遍历 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
思路:
明白二叉树三种遍历方式:
先序遍历:根,左,右
中序遍历:左,根,右
后续遍历:左,右,根
完整代码:
#include <bits/stdc++.h>
#define int long long
const int N = 1e6+10;
int p[N];
struct node
{int v;int ls,rs;
}t[N];
void preorder(int u)//先序遍历
{if(u!=0){std::cout<<t[u].v<<" ";preorder(t[u].ls);preorder(t[u].rs);}
}
void midorder(int u)//中序遍历
{if(u!=0){midorder(t[u].ls);std::cout<<t[u].v<<" ";midorder(t[u].rs);}
}
void postorder(int u)//后续遍历
{if(u!=0){postorder(t[u].ls);postorder(t[u].rs);std::cout<<t[u].v<<" ";}
}
signed main()
{int n;std::cin >> n;for(int i = 1;i <= n;i ++){int x,y;std::cin >> x >> y;t[i].v=i;t[i].ls=x;t[i].rs=y;}preorder(1);std::cout<<"\n";midorder(1);std::cout<<"\n";postorder(1);std::cout<<"\n";return 0;
}
完全二叉树的权值
0完全二叉树的权值 - 蓝桥云课 (lanqiao.cn)
思路:用一个数组存每一层二叉树的权值,再比较哪一层的权值最大
ceil(log(i+1)/log(2)):这个公式用于计算二叉树的深度
完整代码:
#include <bits/stdc++.h>
#define int long long
const int N = 1e5+10;
int sum[N];
signed main()
{int n;std::cin >> n;for(int i = 1;i <= n;i ++){int x;std::cin >> x;int d=ceil(log(i+1)/log(2));sum[d]+=x;}int maxx=-999;int ans=1;for(int i = 1;i <= N;i ++){if(sum[i]>maxx){maxx=sum[i];ans=i;}}std::cout<<ans;return 0;
}
美国血统 American Heritage
P1827 [USACO3.4] 美国血统 American Heritage - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
思路:递归
其他在代码的注释里面
这道题是输出后续遍历,后序是左右根,所以根在最后输出
完整代码:
#include <bits/stdc++.h>
#define int long long
std::string pre,inor;
void work(std::string pre,std::string inor)
{if(pre.empty()) //如果序列空了,就结束return;char root=pre[0];//取前序遍历的根节点int k = inor.find(root);//找到中序序列中根节点的位置pre.erase(pre.begin());//删除前序序列中的根节点std::string leftpre=pre.substr(0,k);std::string rightpre=pre.substr(k);std::string leftinor=inor.substr(0,k);std::string rightinor=inor.substr(k+1);work(leftpre,leftinor);work(rightpre,rightinor);std::cout<<root;
}
signed main()
{std::cin >> inor >> pre;work(pre,inor);return 0;
}
求先序排列
P1030 [NOIP2001 普及组] 求先序排列 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
思路:和前面一题类似,用递归
这道题是求先序排列
先序的顺序是根左右,所以得到根之后要先输出,在递归
完整代码:
#include <bits/stdc++.h>
#define int long long
std::string inor, last;void work(std::string inor, std::string last) {if (last.empty())return;char root = last[last.size()-1];std::cout << root;last.pop_back();//last.erase(last[last.size()-1]);int k = inor.find(root);std::string leftinor = inor.substr(0, k);std::string rightinor = inor.substr(k + 1);std::string leftlast = last.substr(0, k);std::string rightlast = last.substr(k);work(leftinor, leftlast);work(rightinor, rightlast);// std::cout<<root;
}
signed main() {std::cin >> inor >> last;work(inor, last);return 0;
}