zoukankan      html  css  js  c++  java
  • 【思维】迪杰斯特拉升维dp—— swerc Gym

    老套路了。。

    /*
    给定起点(xs,ys),
    终点(xd,yd),
    最大旅程距离B
    汽车的每公里代价C0
    其余交通方式数量T<=100 
    其余交通方式代价[C1..CT]<=100
    车站数量N<=1000
    第i个车站的位置(xi,yi),边数li<=100,每条边(j,mj)表示连向第j个车站,交通方式为mj 
    可以开车从s到任一车站或目的地,从任一车站开车到目的地,但是车站间不得开车
    问在旅程B内的最小代价 
    
    简化:无向图,起点s,终点t,边(u,v,a,b),要求s->t的路径边权b<=B条件下,边权a最小
    直接用二维dij算法,d[u][i]表示到点u,边权b=i情况下a的最小值 
    */
    #include<bits/stdc++.h>
    using namespace std;
    #define ll long long 
    #define N 200005
    
    struct Edge{
        int to,nxt,a,b;
    }e[N<<1];
    int head[N],tot,s,t;
    void add(int u,int v,int b,int a){
        e[tot].to=v;e[tot].a=a;e[tot].b=b;e[tot].nxt=head[u];head[u]=tot++;
    }
    
    int sx,sy,dx,dy,x[N],y[N],B,c0,T,c[N],n;
    vector<pair<int,int> >G[N];
    int calc(int x1,int y1,int x2,int y2){
        return ceil(sqrt(1.0*(x1-x2)*(x1-x2)+(y1-y2)*(y1-y2)));
    }
    void build(){
        memset(head,-1,sizeof head);
        for(int i=1;i<=n;i++){
            for(auto p:G[i]){
                int id=p.first,m=p.second;
                int dis=calc(x[i],y[i],x[id],y[id]);
                add(i,id,dis,dis*c[m]);
                add(id,i,dis,dis*c[m]);        
            }
        }
        s=n+1,t=n+2;
        int dis=calc(sx,sy,dx,dy);
        add(s,t,dis,dis*c0);
        for(int i=1;i<=n;i++){
            dis=calc(sx,sy,x[i],y[i]);
            add(s,i,dis,dis*c0);
            dis=calc(dx,dy,x[i],y[i]);
            add(i,t,dis,dis*c0);
        }
    }
    
    
    struct Node{
        int a,b,id;
        bool operator>(const Node o) const {
            return a>o.a;
        }
    };
    int vis[1005][105],d[1005][105];
    priority_queue<Node,vector<Node>,greater<Node> >pq;
    void dij(){
        for(int i=1;i<=n+2;i++)
            for(int j=0;j<=B;j++)d[i][j]=1e9;
        memset(vis,0,sizeof vis);
        pq.push((Node){0,0,s});
        while(pq.size()){
            Node t=pq.top();pq.pop();
            if(vis[t.id][t.b])continue;
            vis[t.id][t.b]=1;
            int u=t.id,b=t.b,a=t.a;
            for(int i=head[u];i!=-1;i=e[i].nxt){
                int v=e[i].to;
                if(e[i].b+b<=B && !vis[v][e[i].b+b] && d[v][e[i].b+b]>a+e[i].a){
                    d[v][e[i].b+b]=a+e[i].a;
                    pq.push((Node){a+e[i].a,b+e[i].b,v});
                }
            }
        }
    }
    int main(){
        cin>>sx>>sy>>dx>>dy>>B>>c0>>T;
        for(int i=1;i<=T;i++)cin>>c[i];
        cin>>n;
        for(int i=1;i<=n;i++){
            scanf("%d%d",&x[i],&y[i]);
            int l;scanf("%d",&l);
            while(l--){
                int j,m;
                scanf("%d%d",&j,&m);
                G[i].push_back(make_pair(j+1,m));
            }
        }
        build();
        dij();
        int ans=1e9;
        for(int i=0;i<=B;i++)
            ans=min(ans,d[t][i]);
        if(ans>=1e9)cout<<-1<<'
    ';
        else cout<<ans<<'
    ';
    } 
  • 相关阅读:
    备忘录模式---行为型
    观察者模式(Observer)---行为型
    Hadoop基础
    centos执行-查看,复制,删除-命令的脚本
    权限问题
    12月centos单词
    配置集群遇到的问题
    SSH--完全分布式主机设置【克隆过安装过Hadoop的主机后】
    java随机排座位
    NewWord
  • 原文地址:https://www.cnblogs.com/zsben991126/p/13122356.html
Copyright © 2011-2022 走看看