课后算法题求解~

tannoliu 2009-08-12 09:03:28
算法题大概的描述如下:
一个公司要在一条高速路旁建很多旅馆,可供选择的地址共有n个,距离起始点的距离可记为m1,m2,m3,...,mn,起始点可记为0,在每个可能的地址i如果建一个旅馆,可以获得利润pi。
现要求每两个旅馆之间的距离至少为k公里,求一算法可求的在高速路旁建了旅馆后可获得的最大利润。

估计各位大侠也遇过类似的题型,可否帮小弟解答一下?给出递推公式或是伪码最好,感激不尽~
...全文
243 11 打赏 收藏 转发到动态 举报
写回复
用AI写文章
11 条回复
切换为时间正序
请发表友善的回复…
发表回复
tannoliu0 2009-08-25
  • 打赏
  • 举报
回复
问题不错,的确是用动态规划
wutzwjt 2009-08-14
  • 打赏
  • 举报
回复

m[n+1]//各点与起点的距离
p[n+1]// 各点利润
d[n+1]//用于存放建旅馆的点
f=0//总利润
pos=0//表示最近刚找到的建旅馆的点
index=0
d[index] = 0
p[0] = 0
for (i = 1; i <= n; i++)
{
//当第i点与前一个 建 旅馆的点的距离大于等于K时,这一点必选
if (m[i] - m[pos] >= k) {
d[++index] = i;
f = f+ p[i];
pos = i;
}
//当第i点与前一个 建 旅馆的点的距离小于K时,则比较此i点与前一个建 旅馆的点谁的 利润大
//建 利润大者
else if (p[i] > p[pos]) { 
d[index] = i;
f = f-p[pos] + p[i];
pos = i;
}
destinyac 2009-08-14
  • 打赏
  • 举报
回复
这个题目属于动态规划题目,推导公式如下:
假设:f(n)表示 在前n个地点(1~n)中,第n个地点被确定建立旅馆的时候最大收益值。
那么就有:

f(n) = max( f(i) + pn ) 其中 i = 0,....n-1.并且 mn - mi >= k .

初始条件是:
f(0) = p0 ;
附:pn表示,再第n个位置建立旅馆的收益。mn表示,第n个位置距离起始点的距离。
-------------------
并且最优的建立旅馆的收益是(如果有n个地点):
result(n) = max( f(i) ) 其中i = 0 , .... n ;

建立旅馆的地点位置,可以通过回溯一次遍历完成。

具体代码就不写了。
CUSTCOM 2009-08-14
  • 打赏
  • 举报
回复
这种求最优问题通常是用动态规划
zdeepblue 2009-08-14
  • 打赏
  • 举报
回复

#define N 128

int m[N];
float p[N];
double c[N];

int findCandidatePos(int begin, int dist) {
int end = N - 1;
dist += m[begin];
if (m[end] < dist) return N;

int mid = begin;
while (begin < end)
{
mid = (begin + end) / 2;
if (dist < m[mid])
{
end = mid - 1;
}
else if (m[mid] < dist)
{
begin = mid + 1;
}
else
{
break;
}
}

return (m[mid] < dist]) ? mid + 1 : mid;
}


double maxPrice(int curPos, int dist)
{
if (curPos == N) return 0.0;
if (c[curPos] > 0) return c[curPos];

double curMaxPric = 0.0;
int inputCurPos = curPos;
while (curPos < N)
{
int k = findCandidatePos(curPos, dist);
double kMaxPric = 0.0;
while (k < N)
{
double pk = maxPrice(k, dist);
if (pk > kMaxPric)
{
kMaxPric = pk;
}
k = findCandidatePos(k, dist);
}
kMaxPric += p[curPos];
if (kMaxPric > curMaxPric)
{
curMaxPric = kMaxPric;
}
++curPos;
}
c[inputCurPos] = curMaxPric;
return curMaxPric;
}

cl383804490 2009-08-13
  • 打赏
  • 举报
回复
是啊
tannoliu 2009-08-13
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 limit_clear 的回复:]
C/C++ codeint i,p=p1,flag=m1;//p为总利润,flag标记上个旅馆距出发点的距离for(i=2;i<=n;i++)if(mi-flag>=k){p+=pi;flag=mi;}
[/Quote]
楼上的做法显然有问题,如果只有两个位置,利润为p1和p2,且p1<p2,并且它们相聚在k内,那结果就应该是p2,你的解法就是p1.
tannoliu 2009-08-13
  • 打赏
  • 举报
回复
已解决。用动态规划的思想。
xypylove 2009-08-13
  • 打赏
  • 举报
回复
不知道用递归你能接受不?

递归之前先把所有数据按照距离从小到大排序。


int g_iPMax = 0;//最大效益
int n;//总个数

void Search(int iIndex, int iP, int iDistance)
{
if(iIndex == n + 1)
{//递归结束
if(iP > g_iPMax)
{//记录最大收益
g_iPMax = iP;
}
return;
}

if(iP < 0 || mi - iDistance < k)
{//肯定不建
Search(iIndex + 1, iP, iDistance);
}
else if((n > iIndex && mi - iDistance >= k && mi+1 - mi >= k) ||
(n == iIndex && mi - iDistance >= k))
{//肯定建
Search(iIndex + 1, iP + pi, mi);
}
else
{//不一定建,分两种情况递归
Search(iIndex + 1, iP, iDistance);//不建
Search(iIndex + 1, iP + pi, mi);//建
}
}

调用:
g_iPMax = 0;
Search(0, 0, 0);


如果说的不正确的地方请指正,谢谢!
limit_clear 2009-08-12
  • 打赏
  • 举报
回复
int i,p=p1,flag=m1;//p为总利润,flag标记上个旅馆距出发点的距离

for(i=2;i<=n;i++)

if(mi-flag>=k){p+=pi;flag=mi;}

limit_clear 2009-08-12
  • 打赏
  • 举报
回复

int i,p=p1,used[n+1]={0},flag=m1;//p为总利润

for(i=2;i<=n;i++)
{
if(mi-flag>=k){p+=pi;flag=mi;}
}
第1章 绪论 1.1 数据结构的基本概念和术语 1.1.1 引言 1.1.2 数据结构有关概念及术语 1.1.3 数据结构和抽象数据类型(ADT) 1.2 算法描述与分析 1.2.1 什么是算法 1.2.2 算法描述工具——C语言 1.2.3 算法分析技术初步 习一 第2章 线性表 2.1 线性表的定义及其运算 2.1.1 线性表的定义 2.1.2 各种运算简介 2.2 线性表的顺序存储结构(向量) 2.2.1 顺序存储结构(向量) 2.2.2 向量中基本运算的实现 2.3 线性表的链表存储结构 2.3.1 单链表与指针 2.3.2 单链表的基本运算 2.4 循环链表和双向链表 2.4.1 循环链表 2.4.2 双向链表 2.4.3 顺序存储结构与链表存储结构的综合分析与比较 2.5 多项式相加问 2.5.1 多项式相加的链表存储结构 2.5.2 多项式相加的算法实现 2.6 线性表的算法实现举例 2.6.1 实现线性表顺序存储结构及运算的C语言源程序 2.6.2 单链表处理的C语言源程序 习二 第3章 栈和队列 3.1 栈 3.1.1 栈的定义及其运算 3.1.2 栈的顺序存储结构(向量) 3.1.3 栈的链表存储结构 3.1.4 栈的应用 3.2 队列 3.2.1 队列的定义及运算 3.2.2 队列的顺序存储结构(向量) 3.2.3 队列的链表存储结构 3.3 栈和队列的算法实现举例 习三 第4章 串 4.1 串的基本概念 4.2 串的存储结构 4.2.1 串的顺序存储 4.2.2 串的链表存储 4.2.3 串变量的存储映象 4.3 串的运算 4.3.1 串的运算简介 4.3.2 串的匹配运算 4.4 文本编辑 习四 第5章 数组和广义表 5.1 数组的基本概念 5.1.1 数组的概念 5.1.2 数组的顺序表示 5.1.3 特殊矩阵的压缩存储 5.2 稀疏矩阵的三元组存储 5.2.1 三元组表 5.2.2 稀疏矩阵的运算 5.3 稀疏矩阵的十字链表存储 5.3.1 十字链表的组成 5.3.2 十字链表的有关算法 5.4 广义表 5.4.1 广义表的概念和特性 5.4.2 广义表的存储结构 5.4.3 求广义表的深度 5.4.4 广义表的输出 5.4.5 建立广义表的存储结构 5.5 迷宫问五 第6章 树 6.1 树的基本概念和术语 6.1.1 树的定义 6.1.2 树的常用术语 6.1.3 树的表示方法 6.2 二叉树 6.2.1 二叉树的定义 6.2.2 二叉树的重要性质 6.2.3 二叉树的存储结构 6.2.4 二叉树二叉链表的一个生成算法 6.3 遍历二叉树 6.3.1 先根遍历 6.3.2 中根遍历 6.3.3 后根遍历 6.3.4 二叉树遍历算法的应用 6.4 线索二叉树 6.4.1 线索二叉树的基本概念 6.4.2 线索二叉树的逻辑表示图 6.4.3 中根次序线索化算法 6.4.4 在中根线索树上检索某结点的前趋或后继 6.4.5 在中根线索树上遍历二叉树 6.5 二叉树、 树和森林 6.5.1 树的存储结构 6.5.2 树与二叉树之间的转换 6.5.3 森林与二叉树的转换 6.5.4 一般树或森林的遍历 6.6 树的应用 6.6.1 二叉排序树 6.6.2 哈夫曼树及其应用 6.7 二叉树的建立和遍历C语言源程序示例 习六 第7章 图 7.1 图的基本概念和术语 7.1.1 图的基本概念 7.1.2 路径和回路 7.1.3 连通图 7.1.4 顶点的度 7.2 图的存储结构 7.2.1 邻接矩阵 7.2.2 邻接链表 7.3 图的遍历和求图的连通分量 7.3.1 图的建立 7.3.2 图的遍历 7.3.3 求图的连通分量 7.4 图的生成树 7.4.1 生成树的概念 7.4.2 最小生成树 7.4.3 普里姆(Prim)算法和克鲁斯卡尔(Kruskal)算法 7.5 最短路径 7.5.1 单源顶点最短路径问求解 7.5.2 求有向网中每对顶点间的路径 7.6 有向无环图及应用 7.6.1 拓扑排序 7.6.2 关键路径 7.7 图的算法C语言程序实现举例 7.7.1 无向图的邻接表的建立和遍历 7.7.2 有向无环图的拓扑排序和求关键路径 习七 第8章 查找 8.1 基本概念
算法导论(原书第2版)》一书深入浅出,全面地介绍了计算机算法。对每一个算法的分析既易于理解又十分有趣,并保持了数学严谨性。本书的设计目标全面,适用于多种用途。涵盖的内容有:算法在计算中的作用,概率分析和随机算法的介绍。本书专门讨论了线性规划,介绍了动态规划的两个应用,随机化和线性规划技术的近似算法等,还有有关递归求解、快速排序中用到的划分方法与期望线性时间顺序统计算法,以及对贪心算法元素的讨论。本书还介绍了对强连通子图算法正确性的证明,对哈密顿回路和子集求和问的NP完全性的证明等内容。全书提供了900多个练习和思考以及叙述较为详细的实例研究。   《算法导论(原书第2版)》一书内容丰富,对本科生的数据结构课程和研究生的算法课程都是很实用的教材。本书在读者的职业生涯中,也是一本案头的数学参考书或工程实践手册。   在有关算法的书中,有一些叙述非常严谨,但不够全面,另一些涉及了大量的材,但又缺乏严谨性。《算法导论》将严谨性和全面性融为一体。   《算法导论(原书第2版)》一书深入讨论各类算法,并着力使这些算法的设计和分析能为各个层次的读者接受。各章自成体系,可以作为独立的学习单元。算法以英语和伪代码的形式描述,具备初步程序设计经验的人就能看懂。说明和解释力求浅显易懂,不失深度和数学严谨性。   《算法导论(原书第2版)》一书自第1版出版以来,已经成为世界范围内广泛使用的大学教材和专业人员的标准参考书。第2版增加了论述算法作用、概率分析与随机算法、线性规划等几章。同时,对第1版的几乎每一节都作了大量的修订。一项巧妙而又重要的修改是提前引入循环不变式,并在全书中用来证明算法的正确性。在不改变数学和分析重点的前提下,作者将许多数学基础知识从第一部分移到了附录中,并在开始部分加入了一些富有诱导性的材。

64,642

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧