• BZOJ 3550 Vacation


    http://www.lydsy.com/JudgeOnline/problem.php?id=3550

    题意:有3N个数,你需要选出一些数,首先保证任意长度为N的区间中选出的数的个数<=K个,其次要保证选出的数的个数最大。

    思路:和这题类似http://www.cnblogs.com/qzqzgfy/p/5612261.html

    可以转换成不等式然后求费用流。

     1 #include<cstdio>
     2 #include<cmath>
     3 #include<iostream>
     4 #include<algorithm>
     5 #include<cstring>
     6 #define inf 0x7fffffff
     7 int tot,go[200005],next[200005],first[200005],flow[200005],cost[200005];
     8 int dis[200005],vis[200005],op[200005],edge[200005],from[200005],ans,a[200005];
     9 int n,K,S,T,c[200005];
    10 int read(){
    11     int t=0,f=1;char ch=getchar();
    12     while (ch<'0'||ch>'9'){if (ch=='-') f=-1;ch=getchar();}
    13     while ('0'<=ch&&ch<='9'){t=t*10+ch-'0';ch=getchar();}
    14     return t*f;
    15 }
    16 void insert(int x,int y,int z,int l){
    17    tot++;
    18    go[tot]=y;
    19    next[tot]=first[x];
    20    first[x]=tot;
    21    flow[tot]=z;
    22    cost[tot]=l;
    23 }
    24 void add(int x,int y,int z,int l){
    25    insert(x,y,z,l);op[tot]=tot+1;
    26    insert(y,x,0,-l);op[tot]=tot-1;
    27 }
    28 bool spfa(){
    29    for (int i=S;i<=T;i++) dis[i]=0x3f3f3f3f,vis[i]=0;
    30    int h=1,t=1;vis[S]=1;c[1]=S;dis[S]=0;
    31    while (h<=t){
    32        int now=c[h++];
    33        for (int i=first[now];i;i=next[i]){
    34              int pur=go[i];
    35              if (dis[pur]>dis[now]+cost[i]&&flow[i]){
    36                 dis[pur]=dis[now]+cost[i];
    37                 from[pur]=now;
    38                 edge[pur]=i;
    39                 if (vis[pur]) continue;
    40                 c[++t]=pur;
    41                 vis[pur]=1;
    42             }
    43         }
    44         vis[now]=0;
    45     }
    46     return dis[T]!=0x3f3f3f3f;
    47 }
    48 void updata(){
    49     int mn=0x7fffffff;
    50     for (int i=T;i!=S;i=from[i]){
    51           mn=std::min(mn,flow[edge[i]]);
    52     }
    53     for (int i=T;i!=S;i=from[i]){
    54           flow[edge[i]]-=mn;
    55           flow[op[edge[i]]]+=mn;
    56           ans+=mn*cost[edge[i]];
    57     }
    58 }
    59 void mncostflow(){
    60    ans=0;
    61    while (spfa()) updata();
    62    printf("%d
    ",-ans);
    63 }
    64 int main(){
    65     n=read();K=read();S=0;T=2*n+3;
    66     for (int i=1;i<=3*n;i++)
    67         a[i]=read();
    68     for (int i=1;i<=2*n+1;i++)
    69         add(i+1,i,inf,0);
    70     add(1,T,K,0);
    71     add(S,2*n+2,K,0);
    72     for (int i=1;i<=n;i++)
    73         add(i+1,1,1,-a[i]);
    74     for (int i=n+1;i<=n+n;i++)
    75         add(i+1,i+1-n,1,-a[i]);
    76     for (int i=n+n+1;i<=n*3;i++)
    77         add(2*n+2,i-n+1,1,-a[i]);
    78     mncostflow();
    79 }
  • 相关阅读:
    hdu-5492 Find a path(dp)
    hdu-5493 Queue(二分+树状数组)
    bzoj-2243 2243: [SDOI2011]染色(树链剖分)
    codeforces 724
    codeforces 422A A. Borya and Hanabi(暴力)
    codeforces 442C C. Artem and Array(贪心)
    codeforces 442B B. Andrey and Problem(贪心)
    hdu-5918 Sequence I(kmp)
    poj-3739. Special Squares(二维前缀和)
    hdu-5927 Auxiliary Set(树形dp)
  • 原文地址:https://www.cnblogs.com/qzqzgfy/p/5615261.html
Copyright © 2020-2023  润新知