最优二叉搜索树2
2015-10-13 22:22
148 查看
#include "stdio.h" #include "stdlib.h" #include "math.h" #define MAX 100 //此函数返回一棵二叉树的最小平均路长 //n为有序集个数 //a[]中存放在二叉树中的叶节点找到x的概率(成功) //b[]中存放在内节点上找到x的概率(失败) //s[i][j]存放最优子树T(i,j)根节点的元素 //T(i,j)为有序集{xi..xj}关于存取概率{a[i-1],b[i]...b[j],a[j]}的一棵最优二叉树 //w[i][j]表示查询落在区间(xi-1, xj+1)上的概率 //w[i][j] = a[i-1] + b[i] +…+ b[j] + a[j] //m[i][j]为子树{xi..xj}最小平均路长,m[1][n]即为整棵二叉树的最小平均路长 double OBST(int n, double a[], double b[], int s[][MAX], double w[][MAX], double m[][MAX]) { int i, j, r, k; int i1, j1; for(i=0; i<=n; i++) //树中只有叶节点 { w[i+1][i] = a[i]; m[i+1][i] = 0; } for(r=0; r<n; r++) //起止下标差,子树规模 { for(i=1; i<=n-r; i++) //起始下标,当前规模下子树个数 { j = i+r; //终止下标 i1 = s[i][j-1]>i?s[i][j-1]:i; //动态规划加速原理 j1 = s[i+1][j]>i?s[+1][j]:j; //选i作为根节点 //构造T[i][j] 填写w[i][j],m[i][j],s[i][j] m[i][j] = m[i][i1-1] + m[i1+1][j]; //动态规划加速原理 w[i][j] = w[i][j-1] + a[j] + b[j]; s[i][j] = i1; for(k=i1+1; k<=j1; k++) //选取子树中除了i以外的其它节点作为根节点 { //左子树为节点:i,i+1……k-1,右子树为节点:k+1,k+2,……j double u = m[i][k-1] + m[k+1][j]; if(u<m[i][j]) { m[i][j] = u; s[i][j] = k; } } m[i][j] += w[i][j]; } } return m[1] ; } int main() { double a[] = {0.15, 0.1, 0.05,0.05}; double b[] = {0.00, 0.5, 0.1, 0.05}; int n = 4; printf("有序集的概率分布为:\n"); for(int i=0; i<4; i++) { printf("a%d=%.2f,b%d=%.2f\n", i, a[i], i, b[i]); } double m[MAX][MAX], w[MAX][MAX]; int s[MAX][MAX]; double u = OBST(n-1, a, b, s, w, m); printf("二叉搜索树最小平均路长为: %.2f\n", u); return 0; }
相关文章推荐
- HDU4778 Gems Fight!(记忆化搜索+博弈)
- hdu 4568 hunter
- select、poll、epoll之间的区别总结
- eclipse插件启动Genymotion模拟器失败解决方案
- poj 3253 Fence Repair
- abstract interface区别
- leetcode-44 Wildcard Matching 通配符匹配
- HTTP/1.1与HTTP/1.0的区别
- 10.13 js入门
- C++中String类的实现
- 【特种兵PPT教程】簇状柱形图你用对了吗?
- 交叉验证
- iOS 键盘回收实现步骤
- Android官方API Guide学习之二 设备兼容性
- C语言数据结构-树
- Android 五大布局之(一) 线性布局和相对布局
- 编译错误 error C2451: “std::_Unforced”类型的条件表达式是非法的
- 转!!数据库 第一范式(1NF) 第二范式(2NF) 第三范式(3NF)的 联系和区别
- 工厂模式、控制反转及依赖注入
- 第 二 十 九 天:监 控 软 件 之 zabbix