②若a(n-1)>a(n)则存在长度为1的不下降序列a(n-1)或a(n)。
3·一般若从a(i)开始,此时最长不下降序列应该按下列方法求出:
在a(i+1),a(i+2),…,a(n)中,找出一个比a(i)大的且最长的不下降序列,作为它的后继。
4·为算法上的需要,定义一个数组
整数类型二维数组d(N,3)
d(I,1)表示点a(i)
d(I,2)表示从I位置到达N的最长不下降序列长度
d(I,3)表示从I位置开始最长不下降序列的下一个位置
【程序清单】
constmaxn=100;
typetlist=array[1..maxn,1..3]ofinteger;
vard:
tlist;n:
byte;
procedureinit;
vari:
integer;
begin
readln(n);
fori:
=1tondo
beginread(d[i,1]);d[i,2]:
=1;d[i,3]:
=0;end;
end;
proceduremake;
vari,j,p,L:
longint;
begin
fori:
=____
(2)___do
begin
L:
=0;p:
=0;
forj:
=i+1tondo
if(d[i,1]L)then
beginL:
=d[j,2];___(3)___;end;
if___(4)___then
begind[i,2]:
=L+1;d[i,3]:
=p;end;
end
end;
procedureoutput;
vari,L,dmax:
longint;
begin
write(';SOURCE:
');
fori:
=1tondowrite(d[i,1]:
5);
writeln;dmax:
=d[1,2];L:
=1;
fori:
=2ton-1do
ifd[i,2]>dmaxthen
begin___(5)___;L:
=i;end;
write('RESULTIS:
');
whileL<>0do
beginwrite(d[L,1]:
5);L:
=d[L,3]);end;
writeln;
writeln('MAXLENGTH=',d[dmax,2]);
end;
begin
init;
make;
output;
end.
30、求最长不下降序列
(2)n-1downto1(3)p:
=j(4)L>0(5)dmax:
=d[i,2]
1.单源点最短路径:
给定带权有向图G=(v,e),源点v1在v中,求 v1到v中其余各结点的最短路径。
数据结构说明:
cost[I,j]:
表示带权有向图的邻接矩阵
d[j]:
表示从v1到vj的最短路径长度
path[j]:
表示从v1到vj的最短路径
程序如下:
programt5;
constn=5;maxnum=1e10;
type
gr=array[1..n,1..n]ofreal;
dt=array[1..n]ofreal;
jh=setof1..n;
pt=array[1..n]ofjh;
var
s:
jh;cost:
gr;d:
dt;path:
pt;
i,j,k:
integer;
mm:
real;
begin
fori:
=1tondo
forj:
=1tondoread(cost[i,j]);
s:
=[1];
fori:
=2tondo
begin
d[i]:
=cost[1,i];
ifd[i]=[1]+[i]
else___
(1)___
end;
fori:
=1ton-1do
begin
mm:
=maxnum;
forj:
=2tondo
if___
(2)___then
beginmm:
=d[j];k:
=j;end;
s:
=s+[k];
forj:
=2tondo
ifnot(jins)and(cost[k,j]if___(3)___then
begin
d[j]:
=d[k]+cost[k,j];
path[j]:
=___(4)___
end;
end;
writeln;
fori:
=2tondo
begin
writeln('v1->','v',i,':
',d[i]);
write('v1');
forj:
=2tondo
ifjinpath[i]thenwrite('->','v',j);
writeln;
end;
end.
2(好题!
).问题描述:
将n个整数分成k组(k≤n,要求每组不能为空),显然这k个部分均可得到一个各自的积
p1,p2,……pk,定义整数S为:
S=(p1-p2)^2+(p1-p3)^2+……+(p1-pk)^2+(p2-p3)^2+……+(pk-1-pk)^2
问题求解:
求出一种分法,使S为最大(若有多种方案仅记一种〉
程序说明:
数组:
a[1],a[2],...A[N]存放原数
p[1],p[2],...,p[K]存放每个部分的积
b[1],b[2],...,b[N]穷举用临时空间
d[1],d[2],...,d[N]存放最佳方案
程序:
programt6;
Vari,j,n,k:
integer;
sum,cmax:
longint;
a:
array[1..100]ofinteger;
b,d:
array[0..100]ofinteger;
p:
array[1..30]ofinteger;
begin
readln(n,k);
fori:
=1tondoread(a[i]);
fori:
=0tondob[i]:
=1;
cmax:
=0;
while(b[0]=1)do
begin
fori:
=1tokdo___(5)___;
fori:
=1tondo
___(6)___;
sum:
=0;
fori:
=1tok-1do
forj:
=___(7)___do
sum:
=sum+(p[i]-p[j])*(p[i]-p[j]);
if___(8)___then
begin
cmax:
=sum;
fori:
=1tondod[i]:
=b[i];
end;
j:
=n;
while___(9)___doj:
=j-1;
b[j]:
=b[j]+1;
forI:
=j+1tondo___(10)___;
end;
writeln(cmax);
fori:
=1tondowrite(d[i]:
40);
writeln;
end.
1.
(1)path[i]:
=[i]
(2)not(jins)and(d[j](3)(d[k]+cost[k,j])2.(5)p[i]:
=1(6)p[b[i]]:
=p[b[i]]*a[i](7)i+1tok
(8)cmax=1
1.降序组合.给定两个自然数n,r(n>r),输出从数1到n中按降序顺序取r个自然数的所有
组合.例如,n=5,r=3时,有如下组合:
543
542
541
532
531
521
432
431
421
321
程序如下:
programtk1;
varn,r,i,j:
integer;
a:
array[1..20]ofinteger;
begin
write('n,r=');
repeat
readln(n,r);
untiln>r;
i:
=1;a[1]:
=n;writeln('result:
');
repeat
ifi<>rthen
ifa[i]>r-ithen
begin
___
(1)___;i:
=i+1;
end
elsebegin
___
(2)___;
a[I]:
=a[I]-1;
end
else
begin
forj:
=1tordowrite(a[j]:
3);
writeln;
ifa[r]=1then
begin
i:
=i-1;a[i]:
=a[i]-1;
endelse___(3)___
end;
untila[1]=r-1;
end.
2.现在政府计划在某个区域内的的城市间架设高速公路,以使任意两个城市间能够直接或
间接到达,怎样修路,费用最小。
输入文件:
第一行一个整数n(n<=100)表示城市数目。
第二行至第n+1行每行两个数xi,yi(0<=xi,yi<=100)表示第i个城市的坐标(单位:
千米);
输出最小费用(每千米一个单位价格)。
程序如下:
programt6;
constmaxn=100;
typetcity=record
x,y:
real
end;
varc:
array[1..maxn]oftcity;
d:
array[1..maxn,1..maxn]ofreal;
p:
array[1..maxn]ofinteger;
n,i,j,k:
integer;
a,min:
real;
begin
readln(n);
fori:
=1tondoreadln(c[i].x,c[i].y);
fori:
=1tondo
forj:
=1tondo
d[i,j]:
=sqrt(sqr(c[i].x-c[j].x)+sqr(c[i].y-c[j].y));
p[1]:
=0;
fori:
=2tondo___(4)___
fori:
=1ton-1do
begin
min:
=1e10;
forj:
=1tondo
if___(5)___then
begin
min:
=d[p[j],j];
___(6)___
end;
a:
=a+d[p[k],k];
p[k]:
=0;
forj:
=1tondo
if___(7)___thenp[j]:
=k;
end;
writeln(a:
0:
2);
end.
1.a[i+1]:
=a[i]-12.i:
=i-1; 3.a[i]:
=a[i]-1或a[r]:
=a[r]-1;
4.p[i]:
=1; 5.(p[j]>0)and(d[p[j],j])=j;
7.(p[j]>0)and(d[p[j],j]>d[k,j])
1、背包问题:
设有不同价值、不同重量的物品n件,求从这n件物品中选取部分物品的方案,使选中物品的总重量不超过指定的限制重量,但选中物品的价值之和最大。
[算法说明]:
设n件物品的重量分别为w1,w2,…,wn;,物品的价值分别为v1,v2,…,vn。
采用递归寻找物品的选择方案。
设前面已有了多种选择的方案,并保留了其中总价值最大的方案于数组result中,该方案的总价值存于变量maxv。
当前正在考察某一新的方案,其物品选择情况保存于数组option中。
假定当前方案已考虑了前i-1件物品,现在要考虑第i件物品;当前方案已包含的物品的重量之和为tw;至此,若其余物品都选择是可能的话,本方案能达到的总价值的期望值设为tv。
算法引入tv是当一旦当前方案的总价值的期望值也小于前面方案的总价值maxv时,继续考察当前方案变成无意义的工作,应终止当前方案,立即去考察下一个方案。
因为当方案的总价值不比maxv大时,该方案不会再被考察。
这同时保证后面找到的方案一定会比前面的方案更好。
[程序清单]:
programex4;
constmaxn=20;
vari,n,limitw,maxv,totalv:
longint;
w,v:
array[1..maxn]oflongint;
result,option:
array[1..maxn]ofboolean;
proceduretry(i,tw,tv:
longint);
vark:
longint;
begin
iftw+w[i]<=limitwthen
begin
option[i]:
=true;
ifi(1)__________
elsebegin
fork:
=1tondoresult[k]:
=option[k];
maxv:
=tv
end;
____________
(2)_____________;
end;
iftv-v[i]>maxvthen
ifielsebegin
fork:
=1tondoresult[k]:
=option[k];
maxv:
=tv-v[i]
end
end;
begin
write('输入物品种数n:
');readln(n);
writeln('输入各物品的重量和价值:
');
totalv:
=0;
fori:
=1tondo
begin
write('Inputw[',i,'],v[',i,']:
');
readln(w[i],v[i]);
___________(4)_____________;
end;
write('输入限制重量limitw:
');readln(limitw);
maxv:
=0;
fori:
=1tondooption[i]:
=false;
try(1,0,totalv);
write('选择方案为:
');
fori:
=1tondoif____________(5)__________thenwrite(i,'');
writeln;
writeln('总价值为:
',maxv)
end.
2、一矩形阵列由数字0到9组成,数字1到9代表细胞,细胞的定义为沿细胞数字上下左右还是细胞数字则为同一细胞,求给定矩形阵列的细胞个数。
如:
阵列
023*******
1034560500
2045600671
0000000089
有4个细胞。
[算法说明]:
1.从文件中读入m*n矩阵阵列,将其转换为boolean矩阵存入bz数组中;
2.沿bz数组矩阵从上到下,从左到右,找到遇到的第一个细胞;
3.将细胞的位置入队h,并沿其上、下、左、右四个方向上的细胞位置入队,入队后的位置bz数组置为FLASE;
4.将h队的队头出队,沿其上、下、左、右四个方向上的细胞位置入队,入队后的位置bz数组置为FLASE;
5.重复4,直至h队空为止,则此时找出了一个细胞;
6.重复2,直至矩阵找不到细胞;
7.输出找到的细胞数。
[程序清单]:
programxibao;
constdx:
array[1..4]of-1..1=(-1,0,1,0);
dy:
array[1..4]of-1..1=(0,1,0,-1);
varint:
text;name,s:
string;
pic:
array[1..50,1..79]ofbyte;
bz:
array[1..50,1..79]ofboolean;
m,n,i,j,num:
integer;
h:
array[1..4000,1..2]ofbyte;
proceduredoing(p,q:
integer);
vari,t,w,x,y:
integer;
begin
inc(num);
_____________
(1)________________;
t:
=1;w:
=1;
h[1,1]:
=_________
(2)________;
h[1,2]:
=_________(3)________;
repeat
fori:
=1to4do
begin
x:
=h[t,1]+dx[i];y:
=h[t,2]+dy[i];
if(x>0)and(x<=m)and(y>0)and(y<=n)andbz[x,y]
thenbegininc(w);h[w,1]:
=x;h[w,2]:
=y;bz[x,y]:
=false;end;
end;
inc(t);
until________________(4)______________;
end;
begin
fillchar(bz,sizeof(bz),true);num:
=0;
write('inputfile:
');readln(name);
assign(int,name);reset(int);
readln(int,m,n);
fori:
=1to