#include <stdio.h> #include <stdlib.h> // 二叉树结点的定义 struct TreeNode { int val; struct TreeNode *left; struct TreeNode *right;}; // 创建新结点 struct TreeNode *createNode(int val) { struct TreeNode *node = (struct TreeNode *)malloc(sizeof(struct TreeNode)); node->val = val; node->left = NULL; node->right = NULL; return node;} // 合并两棵二叉树 struct TreeNode *mergeTrees(struct TreeNode *t1, struct TreeNode *t2) { if (!t1 && !t2) { return NULL; } else if (!t1) { return t2; } else if (!t2) { return t1; } struct TreeNode *root = createNode(t1->val + t2->val); root->left = mergeTrees(t1->left, t2->left); root->right = mergeTrees(t1->right, t2->right); return root;} // 层次遍历二叉树 void levelOrder(struct TreeNode *root) { if (!root) { return; } // 创建队列 struct TreeNode **queue = (struct TreeNode **)malloc(sizeof(struct TreeNode *) * 1000); int front = 0, rear = 0; queue[rear++] = root; while (front < rear) { struct TreeNode *node = queue[front++]; printf("%d ", node->val); if (node->left) { queue[rear++] = node->left; } if (node->right) { queue[rear++] = node->right; } } free(queue);}int main() { struct TreeNode *t1 = createNode(1); t1->left = createNode(3); t1->right = createNode(2); t1->left->left = createNode(5); struct TreeNode *t2 = createNode(2); t2->left = createNode(1); t2->right = createNode(3); t2->left->right = createNode(4); t2->right->right = createNode(7); struct TreeNode *root = mergeTrees(t1, t2); printf("合并后的二叉树:"); levelOrder(root); printf("\n"); return 0; }解释每行代码
时间: 2024-04-26 10:21:35 浏览: 43
行1:包含标准输入输出库的头文件
行2:包含动态内存分配库的头文件
行4-9:定义二叉树结点的结构体,包含结点值、左右子树指针
行11-17:创建新的二叉树结点,返回结点指针
行19-33:合并两棵二叉树的函数,如果都为空则返回NULL,如果有一棵为空则返回非空的那棵,否则创建新的结点,值为两棵树对应结点的值之和,左右子树递归调用函数合并
行35-53:层次遍历二叉树的函数,如果根节点为空则直接返回,创建长度为1000的队列,队列初始化为空,将根节点加入队列,当队列不为空时,取出队首元素,输出其值,如果左右子树非空,则将左右子树加入队列。最后释放队列内存。
行55-64:主函数,创建两棵二叉树,分别为t1和t2,合并两棵树得到新的根节点,输出合并后的二叉树,调用层次遍历函数输出每个结点的值。
以上是代码的行数和每行的解释。
相关问题
#include <stdio.h> #include <stdlib.h> typedef struct TreeNode { int val; struct TreeNode* left; struct TreeNode* right; } TreeNode; int countNodes(TreeNode* root) { if (!root) { return 0; } return 1 + countNodes(root->left) + countNodes(root->right); } int main() { // 构造一棵二叉树 TreeNode* root = (TreeNode*)malloc(sizeof(TreeNode)); root->val = 1; root->left = (TreeNode*)malloc(sizeof(TreeNode)); root->left->val = 2; root->left->left = NULL; root->left->right = NULL; root->right = (TreeNode*)malloc(sizeof(TreeNode)); root->right->val = 3; root->right->left = NULL; root->right->right = NULL; // 计算二叉树结点个数 int count = countNodes(root); printf("二叉树节点数为: %d\n", count); return 0; }如何增加节点数
要增加二叉树的结点数,可以通过添加新的结点来实现。具体来说,可以按照以下步骤进行:
1. 创建一个新的结点,指定其值和子节点为空。
2. 找到新结点应该插入的位置。一般来说,可以按照二叉搜索树的特点进行插入,即保证左子树结点的值小于根节点的值,右子树结点的值大于根节点的值。
3. 将新结点插入到树中。如果要插入到某个结点的左子树,就将新结点赋值给该结点的左子节点;如果要插入到某个结点的右子树,就将新结点赋值给该结点的右子节点。
以下是一个示例代码,演示如何在上述代码中添加一个新的结点:
```c
#include <stdio.h>
#include <stdlib.h>
typedef struct TreeNode {
int val;
struct TreeNode* left;
struct TreeNode* right;
} TreeNode;
int countNodes(TreeNode* root) {
if (!root) {
return 0;
}
return 1 + countNodes(root->left) + countNodes(root->right);
}
int main() {
// 构造一棵二叉树
TreeNode* root = (TreeNode*)malloc(sizeof(TreeNode));
root->val = 1;
root->left = (TreeNode*)malloc(sizeof(TreeNode));
root->left->val = 2;
root->left->left = NULL;
root->left->right = NULL;
root->right = (TreeNode*)malloc(sizeof(TreeNode));
root->right->val = 3;
root->right->left = NULL;
root->right->right = NULL;
// 添加一个新节点
TreeNode* newNode = (TreeNode*)malloc(sizeof(TreeNode));
newNode->val = 4;
newNode->left = NULL;
newNode->right = NULL;
TreeNode* cur = root;
while (cur->left) { // 找到最左边的叶子结点
cur = cur->left;
}
cur->left = newNode; // 将新节点插入到最左边的叶子结点的左子树中
// 计算二叉树结点个数
int count = countNodes(root);
printf("二叉树节点数为: %d\n", count);
return 0;
}
```
以上代码中,在原有的二叉树基础上添加了一个值为4的新节点,插入到最左边的叶子结点的左子树中。
#include <stdio.h>#include <stdlib.h>#include <string.h>/* 二叉树节点 */typedef struct TreeNode { char val; struct TreeNode *left; struct TreeNode *right;} TreeNode;/* 根据先序序列和中序序列构建二叉树 */TreeNode *buildTree(char *preorder, char *inorder, int preStart, int preEnd, int inStart, int inEnd) { // 先序序列为空,返回NULL if (preStart > preEnd) { return NULL; } // 创建根节点 TreeNode *root = (TreeNode *)malloc(sizeof(TreeNode)); root->val = preorder[preStart]; root->left = root->right = NULL; // 在中序序列中查找根节点的位置 int rootIndex; for (rootIndex = inStart; rootIndex <= inEnd; rootIndex++) { if (inorder[rootIndex] == root->val) { break; } } // 计算左子树的节点个数 int leftSize = rootIndex - inStart; // 递归构建左子树和右子树 root->left = buildTree(preorder, inorder, preStart + 1, preStart + leftSize, inStart, rootIndex - 1); root->right = buildTree(preorder, inorder, preStart + leftSize + 1, preEnd, rootIndex + 1, inEnd); return root;}/* 输出二叉树的后序序列 */void postorderTraversal(TreeNode *root) { if (root == NULL) { return; } postorderTraversal(root->left); postorderTraversal(root->right); printf("%c", root->val);}int main() { char preorder[] = "ABDEGCHF"; char inorder[] = "DBEGAHCF"; // 构建二叉树 TreeNode *root = buildTree(preorder, inorder, 0, strlen(preorder) - 1, 0, strlen(inorder) - 1); // 输出二叉树的后序序列 printf("The postorder traversal of the binary tree is: "); postorderTraversal(root); printf("\n"); return 0;}
这段代码看起来已经很简洁了,不过有一些小的优化可以考虑:
1. 函数参数可以增加 const 修饰符,表示函数不会修改参数的值,这样可以提高代码的可读性和安全性。
2. 二叉树节点结构体可以使用 typedef 来定义,这样代码更加简洁。
3. 开辟内存空间时可以使用 calloc 函数,这样可以避免忘记初始化为 0。
4. 在循环中使用前置自增运算符可以提高代码的效率。
5. 在代码中可以添加注释,提高代码的可读性。
下面是优化后的代码:
```c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/* 二叉树节点 */
typedef struct TreeNode {
char val;
struct TreeNode *left;
struct TreeNode *right;
} TreeNode;
/* 根据先序序列和中序序列构建二叉树 */
TreeNode *buildTree(const char *preorder, const char *inorder, const int preStart, const int preEnd, const int inStart, const int inEnd) {
// 先序序列为空,返回NULL
if (preStart > preEnd) {
return NULL;
}
// 创建根节点
TreeNode *root = (TreeNode *) calloc(1, sizeof(TreeNode));
root->val = preorder[preStart];
root->left = NULL;
root->right = NULL;
// 在中序序列中查找根节点的位置
int rootIndex = inStart;
while (inorder[rootIndex] != root->val) {
++rootIndex;
}
// 计算左子树的节点个数
const int leftSize = rootIndex - inStart;
// 递归构建左子树和右子树
root->left = buildTree(preorder, inorder, preStart + 1, preStart + leftSize, inStart, rootIndex - 1);
root->right = buildTree(preorder, inorder, preStart + leftSize + 1, preEnd, rootIndex + 1, inEnd);
return root;
}
/* 输出二叉树的后序序列 */
void postorderTraversal(const TreeNode *root) {
if (root == NULL) {
return;
}
postorderTraversal(root->left);
postorderTraversal(root->right);
printf("%c", root->val);
}
int main() {
const char preorder[] = "ABDEGCHF";
const char inorder[] = "DBEGAHCF";
// 构建二叉树
TreeNode *root = buildTree(preorder, inorder, 0, strlen(preorder) - 1, 0, strlen(inorder) - 1);
// 输出二叉树的后序序列
printf("The postorder traversal of the binary tree is: ");
postorderTraversal(root);
printf("\n");
return 0;
}
```
阅读全文