日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

NOI2011 智能车比赛

發布時間:2023/12/19 编程问答 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 NOI2011 智能车比赛 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

SPFA。

我們關鍵是要找到關鍵點,包括起點,終點,和相鄰矩形接觸線段的上端點和下端點(如圖有紅色圈住的點為關鍵點)。

我們要做的就是在這些關鍵點之間連邊。

我們把這些關鍵的點拿出來:

其實就是一些豎直的線段。

除了S和T外,從左到右或者從右到左穿過線段所在的直線,必須在線段中穿過去,也就是說有個上邊界和下邊界。

如圖是S到第4條豎直的線段的上邊界l1和下邊界l2。

我們先按X坐標從小到大排序,枚舉邊的起點,向左或者向右連邊,如果遇到豎直的線段,用叉積更改上下邊界即可。

構好圖就直接SPFA即可。

#include<cstdio> #include<cmath> #include<algorithm> #include<cstring>using namespace std;const int maxN=2000; const double INF=1e15; const double EPS=1e-9;inline int dblcmp(double x){if (abs(x)<EPS)return 0;return x>0?1:-1;} inline double sqr(double x){return x*x;}struct Tpoint{double x,y;inline Tpoint(){}inline Tpoint(double _x,double _y){x=_x;y=_y;}};inline double dis(Tpoint a,Tpoint b){return sqrt(sqr(a.x-b.x)+sqr(a.y-b.y));} inline double det(Tpoint p0,Tpoint p1,Tpoint p2){return (p1.x-p0.x)*(p2.y-p0.y)-(p1.y-p0.y)*(p2.x-p0.x);}int N; Tpoint square[maxN+100][2]; Tpoint a[maxN+100][2]; int id[maxN+100][2],cnt; int now,info[2*maxN+100]; struct Tedge{int v,next;double dis;}edge[2*maxN*2*maxN+1000]; double ans,v; Tpoint S,T; int eS,eT,idS,idT;inline void addedge(int u,int v,double dis){now++;edge[now].v=v;edge[now].dis=abs(dis);edge[now].next=info[u];info[u]=now;}inline void solve(Tpoint s,int num,int l){if (num!=idS && num!=idT && num%2==0){addedge(num,num+1,dis(a[l][0],a[l][1]));addedge(num+1,num,dis(a[l][0],a[l][1]));}Tpoint low,high,t1,t2;bool flag=0;for(int i=l-1;i>=1;i--){if (!flag && (id[i][0]==idS || id[i][0]==idT)){addedge(num,id[i][0],dis(s,a[i][0]));addedge(id[i][0],num,dis(s,a[i][0]));continue;}if (!flag){addedge(num,id[i][0],dis(s,a[i][0]));addedge(id[i][0],num,dis(s,a[i][0]));addedge(num,id[i][1],dis(s,a[i][1]));addedge(id[i][1],num,dis(s,a[i][1]));low=a[i][0];high=a[i][1];flag=1;continue;}t1=a[i][0];t2=a[i][1];if ( dblcmp(det(s,low,t1))<=0 && dblcmp(det(s,high,t1))>=0 ){addedge(num,id[i][0],dis(s,a[i][0]));addedge(id[i][0],num,dis(s,a[i][0]));}if ( dblcmp(det(s,low,t2))<=0 && dblcmp(det(s,high,t2))>=0 ){addedge(num,id[i][1],dis(s,a[i][1]));addedge(id[i][1],num,dis(s,a[i][1]));}if (id[i][0]!=idS && id[i][0]!=idT){if ( dblcmp( det(s,low,t2) ) == 1 ) break;if ( dblcmp( det(s,high,t1)) == -1 ) break;if ( dblcmp( det(s,low,t1) ) == -1 ) low=t1;if ( dblcmp( det(s,high,t2))== 1 ) high=t2;}}}int head,tail,queue[7*2*maxN+100]; bool vis[2*maxN+100]; double f[2*maxN+100]; inline double SPFA(){int S=idS,T=idT;for(int i=1;i<=cnt;i++) f[i]=INF;queue[head=tail=0]=S;f[S]=0.0;vis[S]=1;while(head<=tail){int u=queue[(head++)%(7*2*maxN+100)],v,i;double dis;vis[u]=0;for(i=info[u],v=edge[i].v,dis=edge[i].dis;i!=-1;i=edge[i].next,v=edge[i].v,dis=edge[i].dis)if ( dblcmp(dis+f[u]-f[v])==-1 ){f[v]=dis+f[u];if (!vis[v]){vis[v]=1;queue[(++tail)%(7*2*maxN+100)]=v;if ( dblcmp(f[queue[head%(7*2*maxN+100)]]-f[queue[tail%(7*2*maxN+100)]])==1 ) swap(queue[tail%(7*2*maxN+100)],queue[head%(7*2*maxN+100)]);}}}return abs(f[T]);}int main(){freopen("car.in","r",stdin);freopen("car.out","w",stdout);scanf("%d\n",&N);for(int i=1;i<=N;i++)scanf("%lf%lf%lf%lf\n",&square[i][0].x,&square[i][0].y,&square[i][1].x,&square[i][1].y);scanf("%lf%lf\n",&S.x,&S.y);for(int i=1;i<=N;i++)if (dblcmp(square[i][0].x-S.x)<=0 && dblcmp(S.x-square[i][1].x)<=0 && dblcmp(square[i][0].y-S.y)<=0 && dblcmp(S.y-square[i][1].y)<=0){eS=i;break;}scanf("%lf%lf\n",&T.x,&T.y);for(int i=1;i<=N;i++)if (dblcmp(square[i][0].x-T.x)<=0 && dblcmp(T.x-square[i][1].x)<=0 && dblcmp(square[i][0].y-T.y)<=0 && dblcmp(T.y-square[i][1].y)<=0){eT=i;break;}int g=N;N=0;for(int i=1;i<=g;i++){if (i==eS){N++;a[N][0].x=S.x;a[N][0].y=S.y;a[N][1].x=S.x;a[N][1].y=S.y;idS=id[N][0]=id[N][1]=++cnt;}if (i==eT){N++;a[N][0].x=T.x;a[N][0].y=T.y;a[N][1].x=T.x;a[N][1].y=T.y;idT=id[N][0]=id[N][1]=++cnt;}if (i==g) continue;N++;a[N][0].x=square[i][1].x;a[N][0].y=max(square[i][0].y,square[i+1][0].y);a[N][1].x=square[i][1].x;a[N][1].y=min(square[i][1].y,square[i+1][1].y);id[N][0]=++cnt;id[N][1]=++cnt;}memset(info,-1,sizeof(info));now=-1;for(int i=2;i<=N;i++)for(int j=0;j<2;j++)solve(a[i][j],id[i][j],i);ans=SPFA();scanf("%lf\n",&v);ans=ans/v;printf("%0.10lf\n",ans);return 0;} View Code

?

轉載于:https://www.cnblogs.com/maijing/p/4698959.html

總結

以上是生活随笔為你收集整理的NOI2011 智能车比赛的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。