《算法设计与分析》实验指导书.docx
《《算法设计与分析》实验指导书.docx》由会员分享,可在线阅读,更多相关《《算法设计与分析》实验指导书.docx(9页珍藏版)》请在冰豆网上搜索。
《算法设计与分析》实验指导书
算法设计与分析
实验指导书
邵阳学院信息工程系
2010年3月
实验1最大子段和(分治法)
一、实验内容
运用分治法,编制程序求解如下问题:
给定由n个整数(可能有负整数)组成的序列(a1,a2,…,an),最大子段和问题要求该序列形如
的最大值(1<=i<=j<=n),当序列中所有整数均为负整数时,其最大子段和为0。
二、实验要求
1.进一步掌握递归算法的设计思想以及递归程序的调式技术;
2.理解这样一个观点,分治与递归经常同时应用在算法设计之中。
三、主要仪器设备
装有TC或VisualC++的PC机
四、实验步骤
1.算法分析
最大子段和问题的分治策略是:
(1)划分:
按照平衡子问题的原则,将序列(a1,a2,…,an)划分成长度相同的两个子序列(a1,…,an/2)和(an/2+1,…,an),则会出现以下三种情况:
①a1,…,an的最大子段和=a1,…,an/2的最大子段和;
②a1,…,an的最大子段和=an/2+1,…,a的最大子段和;
③a1,…,an的最大子段和=
,且
(2)求解子问题:
对于划分阶段的情况①和②可递归求解,情况③需要分别计算:
,
则s1+s2为情况③的最大子段和。
(3)合并:
比较在划分阶段的三种情况下的最大子段和,取三者之中的较大者为原问题的解。
分析算法的时间性能,对应划分得到的情况①和②,需要分别递归求解,对应情况③,需要两个并列for循环,时间复杂性是O(n),所以,存在如下递推式:
时间复杂性为O(nlogn)。
2.参考代码
#include
intMaxSum(inta[],intleft,intright)
{
intsum=0,leftsum=0,rightsum=0;
intcenter,i,j;
ints1,s2,lefts,rights;
if(left==right)
{
//如果序列长度为1,直接求解
if(a[left]>0)sum=a[left];
elsesum=0;
}
else
{
center=(left+right)/2;//划分
//对应情况①,递归求解
leftsum=MaxSum(a,left,center);
//对应情况②,递归求解
rightsum=MaxSum(a,center+1,right);
//以下对应情况③,先求解s1
s1=0;lefts=0;
for(i=center;i>=left;i--)
{
lefts+=a[i];
if(lefts>s1)s1=lefts;
}
//再求解s2
s2=0;rights=0;
for(j=center+1;j<=right;j++)
{
rights+=a[j];
if(rights>s2)s2=rights;
}
sum=s1+s2;//计算情况③的最大子段和
//合并,在sum、leftsum和rightsum中取较大者
if(sumif(sum}
returnsum;
}
intmain()
{
inta[]={-20,11,-4,13,-5,-2};
intleft=0,right=5;
cout<return0;
}
实验2最长公共子序列问题
一、实验内容
利用动态规划算法编制程序求解下面的问题:
若给定序列X={x1,x2,…,xm},则另一序列Z={z1,z2,…,zk},是X的子序列是指存在一个严格递增下标序列{i1,i2,…,ik}使得对于所有j=1,2,…,k有:
zj=xij。
例如,序列Z={B,C,D,B}是序列X={A,B,C,B,D,A,B}的子序列,相应的递增下标序列为{2,3,5,7}。
给定2个序列X和Y,当另一序列Z既是X的子序列又是Y的子序列时,称Z是序列X和Y的公共子序列。
给定2个序列X={x1,x2,…,xm}和Y={y1,y2,…,yn},找出X和Y的最长公共子序列。
二、实验要求
1.熟悉最长公共子序列问题的算法;
2.初步掌握动态规划算法。
三、主要仪器设备
装有TC或VisualC++的PC机
四、实验步骤
1.算法分析
最长公共子序列问题具有最优子结构性质。
设X={x1,...,xm},Y={y1,...,yn},及它们的最长子序列Z={z1,...,zk},则:
(1)若xm=yn,则zk=xm=yn,且Z[k-1]是X[m-1]和Y[n-1]的最长公共子序列
(2)若xm!
=yn,且zk!
=xm,则Z是X[m-1]和Y的最长公共子序列
(3)若xm!
=yn,且zk!
=yn,则Z是Y[n-1]和X的最长公共子序列
由性质导出子问题的递归结构
当i=0,j=0时,c[i][j]=0
当i,j>0;xi=yi时,c[i][j]=c[i-1][j-1]+1
当i,j>0;xi!
=yi时,c[i][j]=max{c[i][j-1],c[i-1][j]}
2.参考代码
#include
usingnamespacestd;
#definemax100
intL[max][max];//长度矩阵
intS[max][max];//状态矩阵
intCommonOrder(intm,intn,charx[],chary[],charz[])
{
inti,j,k;
for(j=0;j<=n;j++)
L[0][j]=0;//初始化第0行
for(i=0;i<=m;i++)
L[i][0]=0;//初始化第0列
for(i=1;i<=m;i++)
for(j=1;j<=n;j++)
if(x[i]==y[j])
{
L[i][j]=L[i-1][j-1]+1;
S[i][j]=1;
}
elseif(L[i][j-1]>=L[i-1][j])
{
L[i][j]=L[i][j-1];
S[i][j]=2;
}
else
{
L[i][j]=L[i-1][j];
S[i][j]=3;
}
i=m;j=n;k=L[m][n];
while(i>0&&j>0)
{
if(S[i][j]==1)
{
z[k]=x[i];
k--;i--;j--;
}
elseif(S[i][j]==2)
j--;
else
i--;
}
returnL[m][n];
}
intmain()
{
charx[max]={'x','a','b','c','b','d','b'};
chary[max]={'y','a','c','b','b','a','b','d','b','b'};
charz[max];
intm=6,n=9;
intlen=0,i,j;
cout<<"序列X:
"<for(i=1;i<=m;i++)
cout<cout<cout<<"序列Y:
"<for(i=1;i<=n;i++)
cout<cout<len=CommonOrder(m,n,x,y,z);
cout<<"最长公共子序列长度:
"<cout<<"最长公共子序列为:
"<for(i=1;i<=len;i++)
cout<cout<cout<<"长度矩阵:
"<for(i=0;i<=m;i++)
{
for(j=0;j<=n;j++)
cout<cout<}
cout<cout<<"状态矩阵:
"<for(i=0;i<=m;i++)
{
for(j=0;j<=n;j++)
cout<
cout<}
cout<return0;
}
实验3多机调度问题
一、实验内容
利用贪心法设计算法求解如下问题:
要求给出一种作业调度方案,使所给的n个作业在尽可能短的时间内由m台机器加工处理完成。
约定,每个作业均可在任何一台机器上加工处理,但未完工前不允许中断处理。
作业不能拆分成更小的子作业。
分析算法执行效率。
二、实验要求
1.了解多机调度问题,学会分析该问题,并设计相应算法;
2.掌握贪心算法设计思想。
三、主要仪器设备
装有TC或VisualC++的PC机
四、实验步骤
1.算法分析
这个问题是一个NP完全问题,到目前为止还没有一个有效的解法。
对于这一类问题,用贪心选择策略有时可以设计出较好的近似算法。
可以考虑以下的贪心策略:
(1)最长处理时间作业优先的贪心选择策略。
(2)最短处理时间作业优先的贪心选择策略。
(3)作业到达时间优先的贪心选择策略。
2.运行VisualC++集成开发环境,建立控制台工程。
3.编写代码,实现一种贪心算法。
4.假设7个独立的作业由3台机器加工处理,各作业所需的处理时间为:
{2,14,4,6,16,5,3},写出以上算法求解此问题的结果。
。
5.分析算法的运行效率。
五、注意事项
1.对作业进行排序可以使用C++提供的泛型函数sort()来实现。
2.实验报告中,算法分析需要写出算法实现的具体步骤。
3.实验报告中,只需要提供算法实现的主要代码。
实验40-1背包(贪心法)
一、实验内容
运用贪心法,设计贪心策略,编制程序求解如下问题:
给定n个物品和一个容量为C的背包,物品i的重量是Wi,其价值是Vi,0-1背包问题是如何选择装入背包的物品(物品不可以分割),使得装入背包中的物品的总价值最大?
二、实验要求
1.掌握贪心法的设计思想;
2.掌握贪心策略的设计方法以及如何针对特定问题,选取合适的贪心策略。
三、主要仪器设备:
装有TC或VisualC++的PC机
四、实验步骤
1.算法分析
这个问题是一个NP完全问题,到目前为止还没有一个有效的解法。
对于这一类问题,用贪心选择策略有时可以设计出较好的近似算法。
可以考虑以下的贪心策略:
(1)重量最轻的物品优先的贪心选择策略。
(2)重量最重的物品优先优先的贪心选择策略。
(3)价值最大的物品优先的贪心选择策略。
(4)单位价值最大的物品优先的贪心选择策略。
2.运行VisualC++集成开发环境,建立控制台工程。
3.编写代码,实现一种贪心算法。
4.自定义n个物品的重量和价值,以及背包容量C,写出以上算法求解此问题的结果。
。
5.分析算法的运行效率。
五、注意事项
1.排序可以使用C++提供的泛型函数sort()来实现。
2.实验报告中,算法分析需要写出算法实现的具体步骤。
3.实验报告中,只需要提供算法实现的主要代码。