ACM必做50题的解题计算几何.docx

上传人:b****8 文档编号:10338361 上传时间:2023-02-10 格式:DOCX 页数:30 大小:21.12KB
下载 相关 举报
ACM必做50题的解题计算几何.docx_第1页
第1页 / 共30页
ACM必做50题的解题计算几何.docx_第2页
第2页 / 共30页
ACM必做50题的解题计算几何.docx_第3页
第3页 / 共30页
ACM必做50题的解题计算几何.docx_第4页
第4页 / 共30页
ACM必做50题的解题计算几何.docx_第5页
第5页 / 共30页
点击查看更多>>
下载资源
资源描述

ACM必做50题的解题计算几何.docx

《ACM必做50题的解题计算几何.docx》由会员分享,可在线阅读,更多相关《ACM必做50题的解题计算几何.docx(30页珍藏版)》请在冰豆网上搜索。

ACM必做50题的解题计算几何.docx

ACM必做50题的解题计算几何

ACM必做50题的解题-计算几何.txt生活,是用来经营的,而不是用来计较的。

感情,是用来维系的,而不是用来考验的。

爱人,是用来疼爱的,而不是用来伤害的。

金钱,是用来享受的,而不是用来衡量的。

谎言,是用来击破的,而不是用来装饰的。

信任,是用来沉淀的,而不是用来挑战的。

POJ1113WALL

计算几何,求凸包

这题的结果等于这个多边形构成的凸包的周长加上以所给半径为半径的圆的周长

步骤如下:

1)算法首先寻找最最靠下方的点,如果遇到y坐标相同,则寻找x坐标最小的点firstP

2)然后根据所有点相对于firstP的偏角的大小进行排序,遇到偏角相等的,只取距离

firstP最远的点(排序利用自己手写的快排)

3)然后利用Graham算法求凸包

4)最后直接求职

 

#include

#include

#definePI3.1415926

#defineMAX_N1000

usingnamespacestd;

//存储原始输入的坐标值,rad是输入的半径

doublecord[MAX_N+2][2],rad;

intseq[MAX_N+2];

intstack[MAX_N+2];

intn,top;

intfirstP;

intrealN;

voidswap(intpos1,intpos2)

{

inttemp=seq[pos1];

seq[pos1]=seq[pos2];

seq[pos2]=temp;

}

intdir(intnodes,intnode1,intnode2)

{

doublex1=cord[node1][0],y1=cord[node1][1];

doublex2=cord[node2][0],y2=cord[node2][1];

doublesx=cord[nodes][0],sy=cord[nodes][1];

return(x2-sx)*(y1-sy)-(x1-sx)*(y2-sy);

}

doublegetDist(intnode1,intnode2)

{

doublex1=cord[node1][0],y1=cord[node1][1];

doublex2=cord[node2][0],y2=cord[node2][1];

doubleres=sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));

returnres;

}

intcompare(intnode1,intnode2)

{

doublex1=cord[node1][0],y1=cord[node1][1];

doublex2=cord[node2][0],y2=cord[node2][1];

doublesx=cord[firstP][0],sy=cord[firstP][1];

doubletype=dir(firstP,node1,node2);

if(type==0)

{

doubledist1=(x1-sx)*(x1-sx)+(y1-sy)*(y1-sy);

doubledist2=(x2-sx)*(x2-sx)+(y2-sy)*(y2-sy);

if(dist1>dist2)

return-2;

elseif(dist1==dist2)

return0;

else

return2;

}

elseif(type>0)

return1;

else

return-1;

}

voidfastSort(intstart,intend)

{

if(start

{

intcurPos=start;

intposS=start,posE=end+1;

while(true)

{

while(compare(seq[++posS],seq[curPos])<0&&posS

while(compare(seq[--posE],seq[curPos])>0&&posE>start);

if(posS

swap(posS,posE);

else

break;

}

swap(curPos,posE);

fastSort(start,posE-1);

fastSort(posE+1,end);

}

}

voidsortSeq()

{

inti,s=0;

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

{

//最低最左点不参加排序

if(i==firstP)

continue;

seq[++s]=i;

}

realN=n-1;

fastSort(1,realN);

//清理夹角相同但是距离不同的点,只取举例firstP最远的点

i=1;

while(i

{

s=i+1;

//equalanglebutsmallerdistance

while(s<=realN&&compare(seq[i],seq[s])==-2)

{

seq[s]=-1;//置为无效

s++;

}

i=s;

}

}

//寻找凸包

voidfindQ()

{

intnodes,node1,node2,type;

top=0;

stack[top++]=firstP;

ints=1;

intc=0;

while(c<2)

{

if(seq[s]!

=-1)

{

c++;

stack[top++]=seq[s];

}

s++;

}

for(;s<=realN;s++)

{

if(seq[s]==-1)

continue;

while(true)

{

nodes=stack[top-2];

node1=stack[top-1];

node2=seq[s];

type=dir(nodes,node1,node2);

if(type>=0)

top--;

else

break;

}

stack[top++]=seq[s];

}

}

doublegetRes()

{

doubletotalDist=0;

intlastNode=firstP;

intcurNode;

while(top>0)

{

curNode=stack[--top];

totalDist+=getDist(lastNode,curNode);

lastNode=curNode;

}

//totalDist+=getDist(lastNode,firstP);

totalDist+=2*PI*rad;

returntotalDist;

}

intmain()

{

inti;

cin>>n>>rad;

intminX=INT_MAX,minY=INT_MAX;

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

{

cin>>cord[i][0]>>cord[i][1];

if((cord[i][1]

{

firstP=i;

minX=cord[i][0];

minY=cord[i][1];

}

}

sortSeq();

findQ();

doubleres=getRes();

printf("%.0f\n",res);

return0;

}

 

POJ1292WillIndianaJonesGetThere?

题目大意:

英雄Jones现在在位置1,有人在位置2呼救,所以他要过去救他,但是有个条件,他必须在墙上走,其实就是说他只能在图示的线段上走,但是线段间有空隙,所以要用一个长板搭在线段间才能从一个线段到另外一个线段,问怎么找到一个路径使得要使用的长板最小。

题目一眼看下去还比较复杂,毕竟你看到是一堆线段,但是这时候一个很直观的思想就是枚举两个线段间的距离,将每个线段都看成是一个节点,这样其实就化为了一个简单的有向图,这时要寻找最短的长板其实最小生成树的问题,利用Prim算法就可以解决,本题的难处就在于计算线段间的距离跟最小生成树的实现。

计算线段间距离写得很乱,大家包容。

 

#include

#include

#include

floathorDist(intx1,inty1,intL1,intx2,inty2,intL2)

{

if(x2>x1)

{

if(x2>x1+L1)

{

returnsqrt((float)((x2-x1-L1)*(x2-x1-L1)+(y2-y1)*(y2-y1)));

}

else

{

returnabs(y2-y1);

}

}

else

{

if(x1>x2+L2)

{

returnsqrt((float)((x1-x2-L2)*(x1-x2-L2)+(y2-y1)*(y2-y1)));

}

else

{

returnabs(y2-y1);

}

}

}

floatverDist(intx1,inty1,intL1,intx2,inty2,intL2)

{

returnhorDist(y1,x1,-L1,y2,x2,-L2);

}

floathor2verDist(intx1,inty1,intL1,intx2,inty2,intL2)

{

intxHor,yHor,LHor,xVer,yVer,LVer;

if(L1>0)

{

xHor=x1;

yHor=y1;

LHor=L1;

xVer=x2;

yVer=y2;

LVer=-L2;

}

else

{

xHor=x2;

yHor=y2;

LHor=L2;

xVer=x1;

yVer=y1;

LVer=-L1;

}

if(yVer<=yHor&&yHor<=(yVer+LVer))

{

if(xHor<=xVer&&xVer<=(xHor+LHor))

{

return0.0;

}

else

{

if(xVer>(xHor+LHor))

{

returnxVer-xHor-LHor;

}

else

{

returnxHor-xVer;

}

}

}

else

{

if(xHor<=xVer&&xVer<=(xHor+LHor))

{

if(yHor>(yVer+LVer))

{

returnyHor-yVer-LVer;

}

else

{

returnyVer-yHor;

}

}

else

{

if(xVer>(xHor+LHor))

{

if(yHor>(yVer+LVer))

{

returnsqrt((float)(pow((float)(yHor-yVer-LVer),2)+pow((float)(xVer-xHor-LHor),2)));

}

else

{

returnsqrt((float)(pow((float)(yHor-yVer),2)+pow((float)(xVer-xHor-LHor),2)));

}

}

else

{

if(yHor>(yVer+LVer))

{

returnsqrt((float)(pow((float)(yHor-yVer-LVer),2)+pow((float)(xVer-xHor),2)));

}

else

{

returnsqrt((float)(pow((float)(yHor-yVer),2)+pow((float)(xVer-xHor),2)));

}

}

}

}

}

template

TMinFloat(constT&a,constT&b)

{

return(a

a:

b;

};

floatdist(intx1,inty1,intL1,intx2,inty2,intL2)

{

if(L1==0)

{

if(L2==0)

{

returnsqrt((float)(pow((float)(x1-x2),2)+pow((float)(y1-y2),2)));

}

elseif(L2<0)

{

intyTemp=0;

intxTemp=0;

yTemp=y2-L2;

xTemp=x2;

if(y2<=y1&&y1<=yTemp)

{

returnabs(x1-x2);

}

else

{

returnMinFloat(sqrt((float)(pow((float)(x1-x2),2)+pow((float)(y1-y2),2))),sqrt((float)(pow((float)(x1-xTemp),2)+pow((float)(y1-yTemp),2))));

}

}

else

{

intyTemp=0;

intxTemp=0;

yTemp=y2;

xTemp=x2+L2;

if(x2<=x1&&x1<=xTemp)

{

returnabs(y1-y2);

}

else

{

returnMinFloat(sqrt((float)(pow((float)(x1-x2),2)+pow((float)(y1-y2),2))),sqrt((float)(pow((float)(x1-xTemp),2)+pow((float)(y1-yTemp),2))));

}

}

}

if(L2==0)

{

if(L1==0)

{

returnsqrt((float)(pow((float)(x1-x2),2)+pow((float)(y1-y2),2)));

}

elseif(L1<0)

{

intyTemp=0;

intxTemp=0;

yTemp=y1-L1;

xTemp=x1;

if(y1<=y2&&y2<=yTemp)

{

returnabs(x1-x2);

}

else

{

returnMinFloat(sqrt((float)(pow((float)(x1-x2),2)+pow((float)(y1-y2),2))),sqrt((float)(pow((float)(x2-xTemp),2)+pow((float)(y2-yTemp),2))));

}

}

else

{

intyTemp=0;

intxTemp=0;

yTemp=y1;

xTemp=x1+L1;

if(x1<=x2&&x2<=xTemp)

{

returnabs(y1-y2);

}

else

{

returnMinFloat(sqrt((float)(pow((float)(x1-x2),2)+pow((float)(y1-y2),2))),sqrt((float)(pow((float)(x2-xTemp),2)+pow((float)(y2-yTemp),2))));

}

}

}

if(L1*L2>0)

{

if(L1>0)

{

returnhorDist(x1,y1,L1,x2,y2,L2);

}

else

{

returnverDist(x1,y1,L1,x2,y2,L2);

}

}

else

{

returnhor2verDist(x1,y1,L1,x2,y2,L2);

}

}

constintMaxValue=1005;

constfloatMAXFLOAT=10000000000.0;

floatDistArray[MaxValue][MaxValue];

structWALL

{

intx;

inty;

intlength;

};

WALLwalls[MaxValue];

structPointInfo

{

intparent;

floatpath;

boolgoon;

boolcomplete;

};

PointInfoinfo[MaxValue];

floatPrim(intN)

{

inti;

while(true)

{

floatminValue=MAXFLOAT;

intminIndex=-1;

for(i=0;i

{

if(info[i].goon&&!

info[i].complete)

{

if(info[i].path

{

minValue=info[i].path;

minIndex=i;

}

}

}

info[minIndex].complete=true;

if(minIndex==1)

{

break;

}

for(i=0;i

{

if(!

info[i].complete&&i!

=minIndex)

{

info[i].goon=true;

if(DistArray[minIndex][i]

{

info[i].path=DistArray[minIndex][i];

info[i].parent=minIndex;

}

}

}

}

floatlength=0.0;

i=1;

while(info[i].parent!

=-1)

{

floattemp=DistArray[info[i].parent][i];

if(length

{

length=temp;

}

i=info[i].parent;

}

returnlength;

}

intmain()

{

while(true)

{

intN;

inti;

intj;

scanf("%d",&N);

if(N==0)

{

break;

}

for(i=0;i

{

scanf("%d%d%d",&walls[i].x,&walls[i].y,&walls[i].length);

}

memset(DistArray,0,sizeof(DistArray));

for(i=0;i

{

for(j=i+1;j

{

DistArray[i][j]=dist(walls[i].x,walls[i].y,walls[i].length,walls[j].x,walls[j].y,walls[j].length);

DistArray[j][i]=DistArray[i][j];

}

}

for(i=1;i

{

info[i].path=MAXFLOAT;

info[i].goon=false;

info[i].complete=false;

info[i].parent=0;

}

info[0].path=0;

info[0].goon=true;

info[0].complete=false;

info[0].parent=-1;

floatlength=Prim(N);

printf("%.2f\n",length);

}

return0;

}

 

poj2148——ColortheMap——线段部分重合

本题如果把图建完了,其实就是枚举总颜色数后dfs即可。

所以本题的关键就是建图啦。

而建图重要的是解决Twocountriesareconsideredtobe"adjacent"ifanyoftheirterritoriesshareaborderofnon-zero

length.亦即解决两条线段部分重合的问题。

解决部分重合的代码如下:

intcross(const

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 小学教育 > 小学作文

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1