ural 1143. Electric Path(凸包上最短哈密頓路徑)

來源:互聯網
上載者:User

標籤:style   blog   http   get   2014   os   

題目連結:http://acm.timus.ru/problem.aspx?space=1&num=1143

題意:逆時針給一個凸包的n(n<=200)個頂點座標,求一個最短哈密頓路徑的長度。


解法:求最短哈密頓本身是一個NP問題,但是因為是凸包上,可以利用這個做;有一個性質:凸包上的最短哈密頓路徑不會出現交叉。所以可以看出來從一點出發,他要麼和順時針相鄰點串連,要麼和逆時針相鄰點相串連;通過這個性質可以通過dp做:

ans[i][j][0]表示i開始,往後j的點最短路徑長度,ans[i][j][0]表示i開始,往前j的點最短路徑長度;


轉移方程見代碼:有了轉移方程枚舉第一個起始位置就行,複雜度n^3.

/******************************************************* @author:xiefubao*******************************************************/#pragma comment(linker, "/STACK:102400000,102400000")#include <iostream>#include <cstring>#include <cstdlib>#include <cstdio>#include <queue>#include <vector>#include <algorithm>#include <cmath>#include <map>#include <set>#include <stack>#include <string.h>//freopen ("in.txt" , "r" , stdin);using namespace std;#define eps 1e-8#define zero(_) (abs(_)<=eps)const double pi=acos(-1.0);typedef long long LL;const int Max=210;const int INF=1e9+7;struct point{    double x,y;    void read()    {        scanf("%lf%lf",&x,&y);    }} points[Max];double dist[Max][Max];int t=0;int n;double getdis(int i,int j){    return dist[(i+t)%n][(j+t)%n];}double getdist(int i,int j){    i=(i+n)%n;    j=(j+n)%n;    return sqrt((points[i].x-points[j].x)*(points[i].x-points[j].x)+                (points[i].y-points[j].y)*(points[i].y-points[j].y));}double ans[Max][Max][2];double dfs(int i,int j,int st){    i=(i+n)%n;    if(!zero(ans[i][j][st]))        return ans[i][j][st];    if(j==1)        return ans[i][j][st]=getdis(i,i+(st?-1:1));    if(!st)        return ans[i][j][st]=min(dfs(i+1,j-1,0)+getdis(i,i+1),dfs(i+j,j-1,1)+getdis(i,i+j));    else        return ans[i][j][st]=min(dfs(i-1,j-1,1)+getdis(i,i-1),dfs(i-j,j-1,0)+getdis(i,i-j));}double solve(){    memset(ans,0,sizeof ans);    return min(dfs(1,n-2,0)+getdis(0,1),dfs(n-1,n-2,1)+getdis(0,n-1));}int main(){    scanf("%d",&n);    for(int i=0; i<n; i++)        points[i].read();    for(int i=0; i<n; i++)        for(int j=i; j<n; j++)        {            dist[i][j]=getdist(i,j);            dist[j][i]=dist[i][j];        }    double out=INF;    out=min(out,solve());    for(int i=0; i<n-1; i++)    {        t++;        point p=points[0];        for(int j=0; j<n-1; j++)            points[j]=points[j+1];        points[n-1]=p;        out=min(out,solve());    }    printf("%.3f\n",out);    return 0;}


相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.