4
在二元树中找出和为某一值的所有路径(树)
题目:输入一个整数和一棵二元树。
从树的根结点开始往下访问一直到叶结点所经过的所有结点形成一条路径。
打印出和与输入整数相等的所有路径。
例如 输入整数22和如下二元树
10
/ /
5 12
/ /
4 7
则打印出两条路径:10, 12和10, 5, 7。
二元树节点的数据结构定义为:
struct BinaryTreeNode // a node in the binary tree
{
int m_nValue; // value of node
BinaryTreeNode *m_pLeft; // left child of node
BinaryTreeNode *m_pRight; // right child of node
};
分析:先序遍历的方法,用栈配合搜索,比较简单
#include <stdio.h> #include <stdlib.h> struct BinaryTreeNode { int m_nValue; struct BinaryTreeNode *m_pLeft; struct BinaryTreeNode *m_pRight; }; struct BinaryTreeNode *stack[10]; int top = 0; int sum = 0; struct BinaryTreeNode *root; void input() { root = (struct BinaryTreeNode *)malloc(sizeof(struct BinaryTreeNode)); root->m_nValue = 10; root->m_pLeft = (struct BinaryTreeNode *) malloc (sizeof(struct BinaryTreeNode)); root->m_pLeft->m_nValue = 5; root->m_pRight = (struct BinaryTreeNode *) malloc (sizeof(struct BinaryTreeNode)); root->m_pRight->m_nValue = 12; struct BinaryTreeNode *p = root->m_pLeft; p->m_pLeft = (struct BinaryTreeNode *) malloc (sizeof(struct BinaryTreeNode)); p->m_pLeft->m_nValue = 4; p->m_pRight = (struct BinaryTreeNode *) malloc (sizeof(struct BinaryTreeNode)); p->m_pRight->m_nValue = 7; } void pfv(struct BinaryTreeNode *p) { int i; sum += p->m_nValue; stack[top++] = p; if (p->m_pLeft == NULL && p->m_pRight == NULL) { if (sum == 22) { for (i = 0; i < top; i++) { printf("%d ", stack[i]->m_nValue); } printf("\n"); } top--; sum -= p->m_nValue; return; } pfv(p->m_pLeft); pfv(p->m_pRight); top--; sum -= p->m_nValue; } void route() { pfv(root); } int main() { input(); route(); return 0; }
5.查找最小的k个元素(数组)
题目:输入n个整数,输出其中最小的k个。
例如输入1,2,3,4,5,6,7和8这8个数字,则最小的4个数字为1,2,3和4。
分析:才用分治的思想,对序列进行划分。
#include <stdio.h> int vector[9] = {1, 2, 3, 4, 5, 6, 7, 8, 0}; int partition(int left, int right) { int p = left + 1, q = right; while (p <= q) { if (vector[p] > vector[left]) { int t = vector[p]; vector[p] = vector[q]; vector[q--] = t; } else { p++; } } int t = vector[left]; vector[left] = vector[q]; vector[q] = t; return q; } int main() { int k = 3; int t = -1; int left = 0, right = 8; while (t != k) { if (t < k) left = t + 1; else right = t - 1; t = partition(left, right); for (int i = 0; i < 9; i++) { printf("%d ", vector[i]); } printf("\n"); } }
9.判断整数序列是不是二元查找树的后序遍历结果
题目:输入一个整数数组,判断该数组是不是某二元查找树的后序遍历的结果。
如果是返回true,否则返回false。
例如输入5、7、6、9、11、10、8,由于这一整数序列是如下树的后序遍历结果:
8
/ /
6 10
/ / / /
5 7 9 11
因此返回true。
如果输入7、4、6、5,没有哪棵树的后序遍历的结果是这个序列,因此返回false。
分析:注意二叉查找树后序遍历的特性。递归的,根在最后一个节点,前面的节点分为大于根和小于根的两棵子树。
#include <stdio.h> #include <stdlib.h> int treeNodes[7] = {5, 7, 6, 9, 11, 10, 8}; int isBSTree(int left, int root) { int p = left; if (left == root) { return 1; } while (treeNodes[root] > treeNodes[p]) { p++; } int q = p; while (p < root) { if (treeNodes[p++] < treeNodes[root]) return 0; } if (isBSTree(left, q - 1) && isBSTree(q, root - 1)) { return 1; } } int main() { if (isBSTree(0, 6)) { printf("true\n"); } }