zoukankan      html  css  js  c++  java
  • BZOJ 1003 dp+最短路

    1003: [ZJOI2006]物流运输

    题意:m个码头,从码头1到码头m,连续n天都要运送货物。每一天的花费是总路线长度大小,但如果和前一天的路线不一样,要另处加上k元花费。而且有些码头有些天不能用,问这n天的最小费用。

    tags:菜鸡一开始真没想到是dp

    求n天时最小花费,就要想到以天数为阶段进行规划。dp[i][j]表示第i天到第j天走同一条路线的花费,则f[i]=min( f[i], f[j]+dp[j+1][i]+k )。

    #include<bits/stdc++.h>
    using namespace std;
    #pragma comment(linker, "/STACK:102400000,102400000")
    #define FF(i,a,b) for (int i=a;i<=b;i++)
    #define F(i,b,a)  for (int i=b;i>=a;i--)
    #define mes(a,b)  memset(a,b,sizeof(a))
    #define INF 0x3f3f3f3f
    typedef long long ll;
    const int N = 200;
    const ll inf=1e18;
    
    int n, m, k, e1, d1, q[10000], head[N], tot;
    ll c[N][N], dis[N], f[N];
    bool vis[N], use[N], flag[N][N];
    struct Edge{int to, next; ll w;}e[N*N];
    void Addedge(int u, int v, ll w) { e[++tot].to=v, e[tot].w=w, e[tot].next=head[u], head[u]=tot; };
    ll spfa(int x, int y)
    {
        mes(use, 0);  mes(vis, 0);
        FF(i,1,m) dis[i]=inf;   dis[1]=0;
        FF(i,x,y) FF(j,1,m) if(flag[j][i]) use[j]=1;
        int t=0, h=0;
        q[++t]=1, dis[1]=0;
        while(h!=t) {
            int u=q[++h]; vis[u]=1;
            for(int i=head[u]; i; i=e[i].next) {
                int v=e[i].to;  ll w=e[i].w;
                if(use[v]==0 && dis[v]>dis[u]+w) {
                    dis[v]=dis[u]+w;
                    if(vis[v]==0) q[++t]=v, vis[v]=1;
                }
            }
            vis[u]=0;
        }
        return dis[m]*(dis[m]>=inf ? 1 : (y-x+1));
    }
    void Init()
    {
        scanf("%d %d %d %d", &n, &m, &k, &e1);
        int u, v, p, a, b;
        ll w;
        FF(i,1,e1) {
            scanf("%d %d %lld", &u, &v, &w);
            Addedge(u, v, w);  Addedge(v, u, w);
        }
        scanf("%d", &d1);
        FF(i,1,d1) {
            scanf("%d %d %d", &p, &a, &b);
            FF(j,a,b) flag[p][j]=1;
        }
        FF(i,1,n) FF(j,1,i) c[j][i]=spfa(j, i);
    }
    void DP()
    {
        FF(i,1,n) {
            f[i]=c[1][i];
            FF(j,1,i-1) f[i]=min(f[i], f[j]+c[j+1][i]+k);
        }
        printf("%lld
    ", f[n]);
    }
    int main()
    {
        //freopen("in.txt", "r", stdin);
        Init();
        DP();
    
        return 0;
    }
  • 相关阅读:
    Flink基于EventTime和WaterMark处理乱序事件和晚到的数据
    flink 有什么优点
    Flink-Kafka 连接器及exactly-once 语义保证
    腾讯大学
    Qt 获取文件路径、文件名、后缀
    Qt QDir::currentPath()和QAppllication::appllicationDirPath()用法区别
    Qt 程序获取程序所在路径、用户目录路径、临时文件夹等特殊路径的方法
    Qt comboBox设置下拉菜单()
    Qt 快速读写Excel指南
    可见光的波长与频率对照表
  • 原文地址:https://www.cnblogs.com/sbfhy/p/6412166.html
Copyright © 2011-2022 走看看