8606 二叉树的构建及遍历操作
时间限制:1000MS 代码长度限制:10KB
提交次数:2653 通过次数:1597
题型: 编程题 语言: G++;GCC
Description
构造二叉链表表示的二叉树:按先序次序输入二叉树中结点的值(一个字符),'#'字符表示空树,构造二叉链表表示的二叉树T;再输出三种遍历序列。本题只给出部分代码,请补全内容。
#include "stdio.h" #include "malloc.h" #define TRUE 1 #define FALSE 0 #define OK 1 #define ERROR 0 #define INFEASIBLE -1 #define OVERFLOW -2 typedef int Status; typedef char ElemType; typedef struct BiTNode{ ElemType data; struct BiTNode *lchild,*rchild;//左右孩子指针 } BiTNode,*BiTree; Status CreateBiTree(BiTree &T) { // 算法6.4 // 按先序次序输入二叉树中结点的值(一个字符),’#’字符表示空树, // 构造二叉链表表示的二叉树T。 char ch; scanf("%c",&ch); if (ch=='#') T = NULL; else { if (!(T = (BiTNode *)malloc(sizeof(BiTNode)))) return ERROR; ________________________ // 生成根结点 _______________________ // 构造左子树 _________________________ // 构造右子树 } return OK; } // CreateBiTree Status PreOrderTraverse( BiTree T) { // 前序遍历二叉树T的递归算法 //补全代码,可用多个语句 } // PreOrderTraverse Status InOrderTraverse( BiTree T) { // 中序遍历二叉树T的递归算法 //补全代码,可用多个语句 } // InOrderTraverse Status PostOrderTraverse( BiTree T) { // 后序遍历二叉树T的递归算法 //补全代码,可用多个语句 } // PostOrderTraverse int main() //主函数 { //补充代码 }//main
输入格式
第一行:输入一棵二叉树的先序遍历序列
输出格式
第一行:二叉树的先序遍历序列 第二行:二叉树的中序遍历序列 第三行:二叉树的后序遍历序列
输入样例
AB##C##
输出样例
ABC BAC BCA
#include "stdio.h"
#include "malloc.h"
#include<iostream>
using namespace std;
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
#define OVERFLOW -2
typedef int Status;
typedef char ElemType;
typedef struct BiTNode {
ElemType data;
struct BiTNode* lchild, * rchild;//左右孩子指针
} BiTNode, * BiTree;
Status CreateBiTree(BiTree& T) { // 算法6.4
// 按先序次序输入二叉树中结点的值(一个字符),’#’字符表示空树,
// 构造二叉链表表示的二叉树T。
char ch;
scanf("%c", &ch);
if (ch == '#') T = NULL;
else {
if (!(T = (BiTNode*)malloc(sizeof(BiTNode)))) return ERROR;
T->data = ch; // 生成根结点
CreateBiTree(T->lchild); // 构造左子树
CreateBiTree(T->rchild);// 构造右子树
}
return OK;
} // CreateBiTree
17121 求二叉树各种节点数时间限制:1000MS 代码长度限制:10KB 题型: 编程题 语言: G++;GCC Description构造二叉链表表示的二叉树:按先序次序输入二叉树中结点的值(一个字符),'#'字符表示空树,构造二叉链表表示的二叉树T,并求此二叉树中度为2的节点总数,度为1的节点总数,度为0的节点总数 #include "stdio.h" #include "malloc.h" #define TRUE 1 #define FALSE 0 #define OK 1 #define ERROR 0 #define INFEASIBLE -1 #define OVERFLOW -2 typedef int Status; typedef char ElemType; typedef struct BiTNode{ ElemType data; struct BiTNode *lchild,*rchild;//左右孩子指针 } BiTNode,*BiTree; Status CreateBiTree(BiTree &T) { // 算法6.4 // 按先序次序输入二叉树中结点的值(一个字符),’#’字符表示空树, // 构造二叉链表表示的二叉树T。 char ch; scanf("%c",&ch); if (ch=='#') T = NULL; else { if (!(T = (BiTNode *)malloc(sizeof(BiTNode)))) return ERROR; ________________________ // 生成根结点 _______________________ // 构造左子树 _________________________ // 构造右子树 } return OK; } // CreateBiTree int main() //主函数 { //补充代码 }//main 输入格式第一行输入先序次序二叉树中结点 输出格式第一行输出度为2的节点数 第二行输出度为1的节点数 第三行输出度为0的节点数 输入样例ABC###D## 输出样例1 1 2 |
#include "stdio.h"
#include "malloc.h"
#include<iostream>
#include<algorithm>
using namespace std;
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
#define OVERFLOW -2
typedef int Status;
typedef char ElemType;
int degree[3] = { 0 };
typedef struct BiTNode {
ElemType data;
struct BiTNode* lchild, * rchild;//左右孩子指针
} BiTNode, * BiTree;
Status CreateBiTree(BiTree& T) { // 算法6.4
// 按先序次序输入二叉树中结点的值(一个字符),’#’字符表示空树,
// 构造二叉链表表示的二叉树T。
char ch;
scanf("%c", &ch);
if (ch == '#') T = NULL;
else {
if (!(T = (BiTNode*)malloc(sizeof(BiTNode)))) return ERROR;
T->data = ch;// 生成根结点
CreateBiTree(T->lchild); // 构造左子树
CreateBiTree(T->rchild); // 构造右子树
}
return OK;
} // CreateBiTree
void getTreeDegree(BiTree& T) {
if (!T)return;
if (T->lchild && T->rchild) {
degree[2]++;
}
else if (T->lchild || T->rchild) {
degree[1]++;
}
else {
degree[0]++;
}
getTreeDegree(T->lchild);
getTreeDegree(T->rchild);
}
int main() //主函数
{
BiTree T;
CreateBiTree(T);
getTreeDegree(T);
cout << degree[2] << endl << degree[1] << endl << degree[0];
return 0;
}//main
18924 二叉树的宽度时间限制:1000MS 代码长度限制:10KB 题型: 编程题 语言: G++;GCC Description二叉树的宽度指的是具有节点数目最多的那一层的节点个数。 1 / \ 2 3 / 4 答案为2, 第二层节点数最多,为2个节点。 输入格式共n行。 第一行一个整数n,表示有n个结点,编号为1至n,结点1为树根。(1<=n<=50) 第二行至第n行,每行有两个整数x和y,表示在二叉树中x为y的父节点。x第一次出现时y为左孩子 输出格式输出二叉树的宽度。 输入样例5 1 2 1 3 2 4 2 5 输出样例2 |
#include<iostream>
#include<algorithm>
using namespace std;
struct Tree {
int parent;
int left;
int right;//用数组下标表示节点
}tree[100];
int LevelNumber[100];//就是题目那里说的那个宽度,我就翻译成数量了,java写多了喜欢用驼峰命名
void add(int parent, int child) {
tree[child].parent = parent;
if (!tree[parent].left) {//判断做哪边儿子
tree[parent].left = child;
}
else {
tree[parent].right = child;
}
}
void getLevelNumber(int root, int depth) {
LevelNumber[depth]++;
if (tree[root].left) {
getLevelNumber(tree[root].left, depth + 1);
}
if (tree[root].right) {
getLevelNumber(tree[root].right, depth + 1);
}
}
int main() {
int n;
cin >> n;
for (int i = 1; i < n; i++) {
int x, y;
cin >> x >> y;
add(x, y);
}
int root = 0;
for (int i = 1; i <= n; i++) {
if (tree[i].parent == 0) {
root = i;
break;
}
}
getLevelNumber(root, 1);
int ans = 0;
for (int i = 1; i <= n; i++) {
ans = max(ans, LevelNumber[i]);
}
cout << ans << endl;
return 0;
}
18724 二叉树的遍历运算
时间限制:1000MS 代码长度限制:10KB
提交次数:0 通过次数:0
题型: 编程题 语言: G++;GCC
Description
二叉树的三种遍历都可以通过递归实现。 如果我们知道一棵二叉树的先序和中序序列,可以用递归的方法求后序遍历序列。
输入格式
两行,第一行一个字符串,表示树的先序遍历,第二行一个字符串,表示树的中序遍历。 树的结点一律用小写字母表示,且字符串长度不超过30。
输出格式
一个字符串,树的后序序列。
输入样例
abcde bcade
输出样例
cbeda
#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
char preOrder[100];
char inOrder[100];
//前序遍历是根-左子树-右子树
//中序是左子树-根-右子树
//所以按照这个规律,每次递归的preIdx1对应的preOrder就是当前树的根,然后中序中该根的左右分别是他们的子树
//通过中序求出子树长度就可以分别递归去进行后序遍历了
void dfs(int preIdx1, int preIdx2, int inIdx1, int inIdx2) {
if (preIdx1 > preIdx2) {
return;
}
int i;
char node = preOrder[preIdx1];//前序遍历的第一个一定是根节点
for (i = 1; i <= inIdx2; i++) {
if (inOrder[i] == node) {
break;
}
}
int len = i - inIdx1;
dfs(preIdx1 + 1, preIdx1 + len, inIdx1, inIdx1 + len - 1);//pre的左子树的节点数量就是len
dfs(preIdx1 + len + 1, preIdx2, inIdx1 + len + 1, inIdx2);
cout << node;
//左-右-中的后序遍历
}
int main() {
cin >> preOrder + 1;
cin >> inOrder + 1;
dfs(1, strlen(preOrder + 1), 1, strlen(inOrder + 1));
return 0;
}
18923 二叉树的直径时间限制:1000MS 代码长度限制:10KB 题型: 编程题 语言: G++;GCC Description给定一棵二叉树,你需要计算它的直径长度。一棵二叉树的直径长度是任意两个结点路径长度中的最大值。这条路径可能穿过也可能不穿过根结点。 1 / \ 2 3 / \ 4 5 答案为3, 它的长度是路径 [4,2,1,3] 或者 [5,2,1,3]。 输入格式共n行。 第一行一个整数n,表示有n个结点,编号为1至n。 第二行至第n行,每行有两个整数x和y,表示在二叉树中x为y的父节点。x第一次出现时y为左孩子 输出格式输出二叉树的直径。 输入样例5 1 2 1 3 2 4 2 5 输出样例3 |
#include<iostream>
#include<algorithm>
using namespace std;
struct Tree {
int parent;
int left;
int right;//用数组下标表示节点
}tree[100];
int LevelNumber[100];//就是题目那里说的那个宽度,我就翻译成数量了,java写多了喜欢用驼峰命名
void add(int parent, int child) {
tree[child].parent = parent;
if (!tree[parent].left) {//判断做哪边儿子
tree[parent].left = child;
}
else {
tree[parent].right = child;
}
}
int getDepth(int node) {
if (node == 0) {
return 0;
}
else {
int left = getDepth(tree[node].left);
int right = getDepth(tree[node].right);
if (left>right) {
return left + 1;
}
else {
return right + 1;
}
}
}
int main() {
int n;
int Max = 0;
cin >> n;
for (int i = 1; i < n; i++) {
int x, y;
cin >> x >> y;
add(x, y);
}
int root = 0;
for (int i = 1; i <= n; i++) {
int depth = getDepth(tree[i].left) + getDepth(tree[i].right);
Max = max(Max, depth);
}
cout << Max << endl;
return 0;
}
8609 哈夫曼树
时间限制:1000MS 代码长度限制:10KB
提交次数:3178 通过次数:1263
题型: 编程题 语言: G++;GCC
Description
利用静态链表建立赫夫曼树,建树过程中要求左子树权值小于右子树权值,求各结点的编码。要求:叶子结点的个数n及结点值由键盘录入。本题给出程序代码,要求填空以满足测试要求. #include "stdio.h" #include "string.h" #include using namespace std; typedef struct { unsigned int weight; unsigned int parent,lchild,rchild; } HTNode,*HuffmanTree; typedef char **HuffmanCode; void select(HuffmanTree &HT, int n, int &s1, int &s2) {//在HT[1..n]中选择parent为0且weight最小的两个结点, 其序号分别为s1(最小)和s2(次小)。 __________________________ } void createHuffmanTree(HuffmanTree &HT, int n) { //构造哈夫曼树HT int i, m, s1, s2; if (n<=1) return; m = 2 * n - 1; HT = new HTNode[m+1]; // 0号单元未用 for (i=1; i<=m; i++) { //初始化HT数组 HT[i].parent=0;HT[i].lchild=0;HT[i].rchild=0; } for (i=1; i<=n; i++) cin>>HT[i].weight; for (i=n+1; i<=m; i++) // 建哈夫曼树 { //在HT[1..i-1]中选择parent为0且weight最小的两个结点, 其序号分别为s1(最小)和s2(次小) _______________________________ } } void createHuffmanCode(HuffmanTree HT,HuffmanCode &HC,int n) {//--- 从叶子到根逆向求每个字符的哈夫曼编码 --- char *cd = new char[n]; // 分配求编码的工作空间 cd[n-1] = '\0'; // 编码结束符。 int i,c,f,start; for (i=1; i<=n; ++i) { start = n-1; c=i, f=HT[i].parent; while(f)// 从叶子到根逆向求编码 { --start; if (HT[f].lchild==c) cd[start] = '0'; else cd[start] = '1'; c=f,f=HT[f].parent; } HC[i] = new char[n-start];// 为第i个字符编码分配空间 strcpy(HC[i], &cd[start]); // 从cd复制编码(串)到HC } } int main() { int i,n; int *w; HuffmanTree HT; HuffmanCode HC; scanf("%d",&n); //权值个数 HC=new char*[n+1]; //0空间未用 createHuffmanTree(HT,n); createHuffmanCode(HT,HC,n); for (i = 1; i<=n; i++) printf("%s\n",HC[i]); //输出哈夫曼编码 }
输入格式
第一行:权值个数 第二行:输入n个权值,用空格分隔
输出格式
输出n行 每行表示各权值对应的哈夫曼编码
输入样例
8 5 29 7 8 14 23 3 11
输出样例
0001 10 1110 1111 110 01 0000 001
#include "stdio.h"
#include "string.h"
#include<iostream>
using namespace std;
typedef struct
{
unsigned int weight;
unsigned int parent, lchild, rchild;
} HTNode, * HuffmanTree;
typedef char** HuffmanCode;
void select(HuffmanTree& HT, int n, int& s1, int& s2)
{//在HT[1..n]中选择parent为0且weight最小的两个结点, 其序号分别为s1(最小)和s2(次小)。
int i, min1 = 99999, min2=min1+10;
int node1, node2;
node1 = node2 = 0;
for (int i = 1; i <= n; i++) {
if (!HT[i].parent) {
if (HT[i].weight < min1) {
min2 = min1;
s2 = s1;
s1 = i;
min1 = HT[i].weight;
}
else if(HT[i].weight>=min1&&HT[i].weight<min2) {
min2 = HT[i].weight;
s2 = i;
}
}
}
}
void createHuffmanTree(HuffmanTree& HT, int n)
{ //构造哈夫曼树HT
int i, m, s1, s2;
if (n <= 1) return;
m = 2 * n - 1;//n个节点经过合成后会多出n-1个节点
HT = new HTNode[m + 1]; // 0号单元未用
for (i = 1; i <= m; i++) { //初始化HT数组
HT[i].parent = 0; HT[i].lchild = 0; HT[i].rchild = 0;
}
for (i = 1; i <= n; i++)
cin >> HT[i].weight;
for (i = n + 1; i <= m; i++) // 建哈夫曼树
{ //在HT[1..i-1]中选择parent为0且weight最小的两个结点, 其序号分别为s1(最小)和s2(次小)
int s1, s2;
select(HT, i - 1, s1, s2);
HT[s1].parent = HT[s2].parent = i;
HT[i].lchild = s1, HT[i].rchild = s2;
HT[i].weight = HT[s1].weight + HT[s2].weight;
}
}
void createHuffmanCode(HuffmanTree HT, HuffmanCode& HC, int n)
{//--- 从叶子到根逆向求每个字符的哈夫曼编码 ---
char* cd = new char[n]; // 分配求编码的工作空间
cd[n - 1] = '\0'; // 编码结束符。
int i, c, f, start;
for (i = 1; i <= n; ++i)
{
start = n - 1;
c = i, f = HT[i].parent;
while (f)// 从叶子到根逆向求编码
{
--start;
if (HT[f].lchild == c) cd[start] = '0';
else cd[start] = '1';
c = f, f = HT[f].parent;
}
HC[i] = new char[n - start];// 为第i个字符编码分配空间
strcpy(HC[i], &cd[start]); // 从cd复制编码(串)到HC
}
}
int main()
{
int i, n;
int* w;
HuffmanTree HT;
HuffmanCode HC;
scanf("%d", &n); //权值个数
HC = new char* [n + 1]; //0空间未用
createHuffmanTree(HT, n);
createHuffmanCode(HT, HC, n);
for (i = 1; i <= n; i++)
printf("%s\n", HC[i]); //输出哈夫曼编码
}
#include<iostream>
#include<algorithm>
#include<stack>
#include<queue>
using namespace std;
typedef struct BinaryNode {
int data;
struct BinaryNode* left, * right;
}BinaryNode, * BinaryTree;
void InsertToBinaryTree(BinaryTree &T,int data) {
if (!T) {
BinaryTree S;
S = new BinaryNode;
S->data = data;
S->left = S->right = NULL;
T = S;
}
else if (data < (T->data)) {
InsertToBinaryTree(T->left, data);
}
else if (data > T->data) {
InsertToBinaryTree(T->right, data);
}
}
void PreOrderTraverse(BinaryTree T) {
if (T == NULL) {
return;
}
cout << T->data << ' ';
PreOrderTraverse(T->left);
PreOrderTraverse(T->right);
}
void PreOrderTraverse2(BinaryTree T) {
stack<BinaryTree>S;
BinaryTree p = T;
while (p) {
cout << p->data << ' ';
S.push(p);
p = p->left;
}
while (!S.empty()) {
p = S.top();
S.pop();
cout << p->data << ' ';
p = p->right;
while (p) {
cout << p->data << ' ';
S.push(p);
p = p->left;
}
}
cout << endl;
}
void InOrderTraverse(BinaryTree T) {
if (T == NULL) {
return;
}
InOrderTraverse(T->left);
cout << T->data << ' ';
InOrderTraverse(T->right);
}
void InOrderTraverse2(BinaryTree T) {
stack<BinaryTree>S;
BinaryTree p = T;
while (p || !S.empty()) {
if (p) {
S.push(p);
p = p->left;
}
else {
p = S.top();
S.pop();
cout << p->data << ' ';
p = p->right;
}
}
cout << endl;
}
void PostOrderTraverse(BinaryTree T) {
if (T == NULL) {
return;
}
PostOrderTraverse(T->left);
PostOrderTraverse(T->right);
cout << T->data << ' ';
}
void PostOrderTraverse2(BinaryTree T) {
stack<BinaryTree>S;
BinaryTree p = T, pre = NULL;
while (p) {
S.push(p);
p = p->left;
}
while (!S.empty()) {
p = S.top();
if ((p->left == NULL && p->right == NULL) || (p->left == pre && p->right == NULL) || (p->right == pre)) {
cout << p->data << ' ';
pre = p;
S.pop();
}
else {
p = p->right;
while (p) {
S.push(p);
p = p->left;
}
}
}
cout << endl;
}
void LTB(BinaryTree T) {
queue<BinaryTree>q;
BinaryTree p=T;
q.push(p);
while (!q.empty()) {
p = q.front();
cout << p->data << ' ';
q.pop();
if (p->left != NULL)
q.push(p->left);
if (p->right != NULL)
q.push(p -> right);
}
cout << endl;
}
int SearchKey(BinaryTree T, int key) {
if (!T) {
return 0;
}
else if (T->data == key) {
return 1;
}
else if (T->data > key) {
return SearchKey(T->left, key);
}
else if (T->data < key) {
return SearchKey(T->right, key);
}
}
void SwapChildNode(BinaryTree &T) {
if (!T) {
return;
}
BinaryTree t = T->left;
T->left = T->right;
T->right = t;
SwapChildNode(T->left);
SwapChildNode(T->right);
}
int NodeNumber(BinaryTree T) {
if (!T)return 0;
else if (T->left == NULL && T -> right == NULL)
{
return 1;
}
else {
return NodeNumber(T->left) + NodeNumber(T -> right);
}
}
int Depth(BinaryTree T) {
if (!T)return 0;
return max(Depth(T->left), Depth(T->right)) + 1;
}
int main() {
BinaryTree T = NULL;
int n, data;
cin >> n;
for (int i = 0; i < n; i++) {
cin >> data;
InsertToBinaryTree(T, data);
}
PreOrderTraverse(T);
cout << endl;
InOrderTraverse(T);
cout << endl;
PostOrderTraverse(T);
cout << endl;
int key;
cin >> key;
cout << SearchKey(T, key) << endl;
cin >> key;
cout << SearchKey(T, key) << endl;
int insertKey;
cin >> insertKey;
InsertToBinaryTree(T,insertKey);
PreOrderTraverse(T);
cout << endl;
InOrderTraverse(T);
cout << endl;
PostOrderTraverse(T);
cout << endl;
InOrderTraverse2(T);
LTB(T);
SwapChildNode(T);
PreOrderTraverse(T);
cout << endl;
InOrderTraverse(T);
cout << endl;
PostOrderTraverse(T);
cout << endl;
SwapChildNode(T);
PreOrderTraverse(T);
cout << endl;
InOrderTraverse(T);
cout << endl;
PostOrderTraverse(T);
cout << endl;
cout << Depth(T) << endl;
cout << NodeNumber(T) << endl;
return 0;
}
8608 实现二叉排序树的各种算法(2)时间限制:1000MS 代码长度限制:10KB 题型: 编程题 语言: G++;GCC Description用函数实现如下二叉排序树算法: (1) 插入新结点 (2) 前序、中序、后序遍历二叉树 (3) 中序遍历的非递归算法 (4) 层次遍历二叉树 (5) 在二叉树中查找给定关键字(函数返回值为成功1,失败0) (6) 交换各结点的左右子树 (7) 求二叉树的深度 (8) 叶子结点数 输入格式第一行:准备建树的结点个数n 第二行:输入n个整数,用空格分隔 第三行:输入待查找的关键字 第四行:输入待查找的关键字 第五行:输入待插入的关键字 输出格式第一行:二叉树的先序遍历序列 第二行:二叉树的中序遍历序列 第三行:二叉树的后序遍历序列 第四行:查找结果 第五行:查找结果 第六行~第八行:插入新结点后的二叉树的先、中、序遍历序列 第九行:插入新结点后的二叉树的中序遍历序列(非递归算法) 第十行:插入新结点后的二叉树的层次遍历序列 第十一行~第十三行:第一次交换各结点的左右子树后的先、中、后序遍历序列 第十四行~第十六行:第二次交换各结点的左右子树后的先、中、后序遍历序列 第十七行:二叉树的深度 第十八行:叶子结点数 输入样例7 40 20 60 18 50 56 90 18 35 30 输出样例40 20 18 60 50 56 90 18 20 40 50 56 60 90 18 20 56 50 90 60 40 1 0 40 20 18 30 60 50 56 90 18 20 30 40 50 56 60 90 18 30 20 56 50 90 60 40 18 20 30 40 50 56 60 90 40 20 60 18 30 50 90 56 40 60 90 50 56 20 30 18 90 60 56 50 40 30 20 18 90 56 50 60 30 18 20 40 40 20 18 30 60 50 56 90 18 20 30 40 50 56 60 90 18 30 20 56 50 90 60 40 4 4 |