• 洛谷 P2488 [SDOI2011]工作安排


    题目描述

    你的任务是制定出一个产品的分配方案,使得订单条件被满足,并且所有员工的愤怒值之和最小。由于我们并不想使用Special Judge,也为了使选手有更多的时间研究其他两道题目,你只需要输出最小的愤怒值之和就可以了。

    输入输出格式

    输入格式:

    输出格式:

    仅输出一个整数,表示最小的愤怒值之和。

    输入输出样例

    输入样例#1:
    2 3
    2 2 2
    1 1 0
    0 0 1
    1
    2
    1 10
    1
    2
    1 6
    输出样例#1:
    24

    说明

    一看,哇,修车,美食节,直接拆点,跑费用流,光荣T掉,还WA了几个点(原因不明)

    然而这个题和修车不一样,每一份流量的性质都是相同的,没有拆点的必要,直接拆边就好了

    SS--(C[i],0)-->物品i--(INF,0)-->员工j---(S[j][k]-s[j][k-1],W[i][j])-->TT

    把每个员工到TT的边拆成S[i]+1条即可

      1 #include <iostream>
      2 #include <cstdlib>
      3 #include <cstdio>
      4 #include <algorithm>
      5 #include <string>
      6 #include <cstring>
      7 #include <cmath>
      8 #include <map>
      9 #include <stack>
     10 #include <set>
     11 #include <vector>
     12 #include <queue>
     13 #include <time.h>
     14 #define eps 1e-7
     15 #define INF 0x3f3f3f3f
     16 #define MOD 1000000007
     17 #define rep0(j,n) for(int j=0;j<n;++j)
     18 #define rep1(j,n) for(int j=1;j<=n;++j)
     19 #define pb push_back
     20 #define set0(n) memset(n,0,sizeof(n))
     21 #define ll long long
     22 #define ull unsigned long long
     23 #define iter(i,v) for(edge *i=head[v];i;i=i->nxt)
     24 #define max(a,b) (a>b?a:b)
     25 #define min(a,b) (a<b?a:b)
     26 #define print_runtime printf("Running time:%.3lfs
    ",double(clock())/1000.0)
     27 #define TO(j) printf(#j": %d
    ",j);
     28 //#define OJ
     29 using namespace std;
     30 const int MAXINT = 100010;
     31 const int MAXNODE = 700;
     32 const int MAXEDGE = 1000000;
     33 char BUF,*buf;
     34 int read(){
     35     char c=getchar();int f=1,x=0;
     36     while(!isdigit(c)){if(c=='-') f=-1;c=getchar();}
     37     while(isdigit(c)){x=x*10+c-'0';c=getchar();}
     38     return f*x;
     39 }
     40 char get_ch(){
     41     char c=getchar();
     42     while(!isalpha(c)) c=getchar();
     43     return c;
     44 }
     45 //------------------- Head Files ----------------------//
     46 int cnt,dis[MAXNODE],q[MAXNODE*MAXNODE],inq[MAXNODE],n,m,C[300],ok[300][300],S[300],T[300][7],W[300][7],SS,TT;
     47 struct edge{
     48     int u,v,c,cost;
     49     edge *nxt;
     50     edge(){}
     51     edge(int _u,int _v,int _c,int _cost,edge *_nxt):u(_u),v(_v),c(_c),cost(_cost),nxt(_nxt){}
     52 }mp[MAXEDGE],*head[MAXNODE],*from[MAXNODE];
     53 void addedge(int u,int v,int c,int cost){
     54     mp[cnt]=edge(u,v,c,cost,head[u]);
     55     head[u]=&mp[cnt++];
     56     mp[cnt]=edge(v,u,0,-cost,head[v]);
     57     head[v]=&mp[cnt++];
     58 }
     59 int spfa(int ss,int tt){
     60     memset(dis,INF,sizeof(dis));
     61     dis[ss]=0;
     62     int *h,*t;
     63     h=t=q;
     64     *t++=ss;
     65     while(h!=t){
     66         int p=*h++;
     67         inq[p]=0;
     68         iter(i,p){
     69             if(i->c&&dis[i->v]>dis[p]+i->cost){
     70                 dis[i->v] = dis[p]+i->cost;
     71                 from[i->v]=i;
     72                 if(!inq[i->v]){
     73                     *t++=i->v;
     74                     inq[i->v]=1;
     75                 }
     76             }
     77         }
     78     }
     79     return dis[tt]!=INF;
     80 }
     81 edge *rev(edge *e){
     82     return &mp[(e-mp)^1];
     83 }
     84 ll extend(int ss,int tt){
     85     ll c=INF,cost=0;
     86     int p=tt;
     87     while(p!=ss){
     88         c=min(c,from[p]->c);
     89         cost+=from[p]->cost;
     90         p=from[p]->u;
     91     }
     92     p=tt;
     93     while(p!=ss){
     94         from[p]->c-=c;
     95         rev(from[p])->c+=c;
     96         p=from[p]->u;
     97     }
     98     return c*cost;
     99 }
    100 ll cost_flow(int ss,int tt){
    101     ll ans=0;
    102     while(spfa(ss,tt)){
    103         ans+=extend(ss,tt);
    104     }
    105     return ans;
    106 }
    107 void get_input();
    108 void work();
    109 int main() {
    110     get_input();
    111     work();
    112     return 0;
    113 }
    114 void work(){
    115     SS=698;TT=699;
    116     rep0(i,n){
    117         addedge(SS,i,C[i],0);
    118         rep0(j,m) if(ok[j][i]) addedge(i,n+j,INF,0);
    119     }
    120     rep0(i,m){
    121         if(S[i]==0){
    122             addedge(n+i,TT,INF,W[i][0]);
    123         }else{
    124             addedge(n+i,TT,T[i][0],W[i][0]);
    125             for(int j=1;j<S[i];j++){
    126                 addedge(n+i,TT,T[i][j]-T[i][j-1],W[i][j]);
    127             }
    128             addedge(n+i,TT,INF,W[i][S[i]]);
    129         }
    130     }
    131     printf("%lld
    ",cost_flow(SS,TT));
    132 }
    133 void get_input(){
    134     m=read();n=read();
    135     rep0(i,n) C[i]=read();
    136     rep0(i,m) rep0(j,n) ok[i][j]=read();
    137     rep0(i,m){
    138         S[i]=read();
    139         rep0(j,S[i]) T[i][j]=read();
    140         rep0(j,S[i]+1) W[i][j]=read();
    141     }
    142 }
    143 /*
    144 2 3
    145 2 2 2
    146 1 1 0
    147 0 0 1
    148 1
    149 2
    150 1 10
    151 1
    152 2
    153 1 6
    154 */
  • 相关阅读:
    linux umask使用详解
    Linux 解压压缩命令
    linux命令:tail 命令
    linux命令:head 命令
    linux下cat命令详解
    linux命令:rm 命令
    linux命令:mv命令
    Linux 的cp命令
    文件权限详解
    Linux ls命令参数详解
  • 原文地址:https://www.cnblogs.com/LoveYayoi/p/6913912.html
Copyright © 2020-2023  润新知