zoukankan      html  css  js  c++  java
  • Optimal Marks SPOJ

    传送门

    一个无向图,每个点有点权,某些点点权确定了,某些点由你来确定,边权为两个点的异或和,要使边权和最小。

    这不是一道按位做最小割的大水题么

    非常开心地打了,还非常开心地以为有spj,然后非常开心地Wa了

    才发现在边权和最小的条件下还要让点权和最小。

    这可咋整啊,难不成要费用流。

    然后悄悄搜了下题解发现了巧妙的解决方法,把原来建的图中的边权都扩大10000倍,然后在选1的地方边权再悄悄加上1

    把它看成10000和1两条边的话,相当于优先考虑大边最小,大边最小的前提下小边最小,即答案。

      1 //Achen
      2 #include<algorithm>
      3 #include<iostream>
      4 #include<cstring>
      5 #include<cstdlib>
      6 #include<vector>
      7 #include<cstdio>
      8 #include<queue>
      9 #include<cmath>
     10 #include<set>
     11 #include<map>
     12 #define Formylove return 0
     13 #define For(i,a,b) for(int i=(a);i<=(b);i++)
     14 #define Rep(i,a,b) for(int i=(a);i>=(b);i--)
     15 const int M=3500*10,N=550;
     16 typedef long long LL;
     17 typedef double db;
     18 using namespace std;
     19 int n,m,k,qd[N],val[N],ec[M][2];
     20 
     21 template<typename T>void read(T &x)  {
     22     char ch=getchar(); x=0; T f=1;
     23     while(ch!='-'&&(ch<'0'||ch>'9')) ch=getchar();
     24     if(ch=='-') f=-1,ch=getchar();
     25     for(;ch>='0'&&ch<='9';ch=getchar()) x=x*10+ch-'0'; x*=f;
     26 }
     27 
     28 struct edge {
     29     int u,v,cap,fl,nx;
     30     edge(){}
     31     edge(int u,int v,int cap,int fl,int nx):u(u),v(v),cap(cap),fl(fl),nx(nx){} 
     32 }e[M];
     33 
     34 int ecnt=1,fir[N];
     35 void add(int u,int v,int cap) {
     36     e[++ecnt]=edge(u,v,cap,0,fir[u]); fir[u]=ecnt;
     37     //printf("%d->%d:%d
    ",u,v,cap);
     38     e[++ecnt]=edge(v,u,0,0,fir[v]); fir[v]=ecnt;
     39 }
     40 
     41 queue<int>que;
     42 int d[N];
     43 void bfs(int s,int t) {
     44     que.push(t);
     45     For(i,1,n) d[i]=n;
     46     d[t]=0;
     47     while(!que.empty()) {
     48         int x=que.front();
     49         que.pop();
     50         for(int i=fir[x];i;i=e[i].nx) {
     51             int y=e[i].v;
     52             if(d[y]==n&&e[i].cap==0) {
     53                 d[y]=d[x]+1;
     54                 que.push(y); 
     55             }
     56         }
     57     }
     58 }
     59 
     60 #define inf 1e9
     61 int p[N];
     62 int calc(int s,int t) {
     63     int fl=inf;
     64     for(int i=t;i!=s;i=e[p[i]].u)
     65         fl=min(fl,e[p[i]].cap-e[p[i]].fl);
     66     for(int i=t;i!=s;i=e[p[i]].u) 
     67         e[p[i]].fl+=fl,e[p[i]^1].fl-=fl;
     68     return fl;
     69 }
     70 
     71 int c[N],cur[N];
     72 int isap(int s,int t) {
     73     For(i,0,n) c[i]=0;
     74     bfs(s,t);
     75     For(i,1,n) cur[i]=fir[i],c[d[i]]++;
     76     int rs=0;
     77     for(int x=s;d[x]<n;) {
     78         if(x==t) {
     79             rs+=calc(s,t);
     80             x=s;
     81         }
     82         int ok=0;
     83         for(int &i=cur[x];i;i=e[i].nx) if(e[i].cap>e[i].fl&&d[e[i].v]+1==d[x]) {
     84             ok=1; p[x=e[i].v]=i; break;
     85         }
     86         if(!ok) {
     87             int D=n; cur[x]=fir[x];
     88             for(int i=fir[x];i;i=e[i].nx) if(e[i].cap>e[i].fl)
     89                 D=min(D,d[e[i].v]+1);
     90             if(!(--c[d[x]])) break; 
     91             c[d[x]=D]++;
     92             if(x!=s) x=e[p[x]].u;
     93         }
     94     }
     95     return rs;
     96 }
     97 
     98 void init() {
     99     ecnt=1;
    100     memset(fir,0,sizeof(fir));
    101 }
    102 
    103 int vis[N];
    104 void dfs(int x) {
    105     vis[x]=1;
    106     for(int i=fir[x];i;i=e[i].nx) if(!vis[e[i].v]&&e[i].cap>e[i].fl)
    107         dfs(e[i].v);
    108 } 
    109 
    110 int main() {
    111 #ifdef ANS
    112     freopen(".in","r",stdin);
    113     freopen(".out","w",stdout);
    114 #endif
    115     int T; read(T);
    116     while(T--) {
    117         read(n); read(m);
    118         For(i,1,m) {
    119             read(ec[i][0]);
    120             read(ec[i][1]);
    121         }
    122         read(k);
    123         For(i,1,n) val[i]=0,qd[i]=0;
    124         For(i,1,k) {
    125             int x;
    126             read(x); qd[x]=1;
    127             read(val[x]);
    128         }
    129         int s=n+1,t=n+2;
    130         For(i,0,30) {
    131             init();
    132             For(j,1,n) {
    133                 if(qd[j]) {
    134                     if(val[j]&(1<<i)) {
    135                         add(s,j,10000);
    136                         add(j,t,inf);
    137                     } 
    138                     else {
    139                         add(s,j,inf);
    140                         add(j,t,10000);
    141                     }
    142                 }
    143                 else {
    144                     add(s,j,10001);
    145                     add(j,t,10000);
    146                 }
    147             }
    148             For(j,1,m) {
    149                 int u=ec[j][0],v=ec[j][1];
    150                 add(u,v,10000); add(v,u,10000);
    151             }
    152             n+=2;
    153             isap(s,t); 
    154             n-=2;
    155             memset(vis,0,sizeof(vis));
    156             dfs(s);
    157             For(j,1,n) if(!vis[j]) val[j]|=(1<<i);
    158         }
    159         For(i,1,n) printf("%d
    ",val[i]);
    160         //printf("%d
    ",val[n]);
    161         /*long long ans=0;
    162         for(int i=1;i<=m;i++) {
    163             int u=ec[i][0],v=ec[i][1];
    164             ans+=(val[u]^val[v]);
    165         }
    166         printf("%lld
    ",ans);*/
    167     }
    168     Formylove;
    169 }
    170 /*
    171 1
    172 6 7
    173 1 2
    174 2 4
    175 1 3
    176 2 3
    177 4 3
    178 1 5
    179 5 6
    180 4
    181 1 5
    182 3 1
    183 4 7
    184 6 2
    185 */
    View Code
  • 相关阅读:
    RTC驱动程序分析
    Linux下的RTC子系统
    [置顶] 谈EXPORT_SYMBOL使用
    《Linux内核修炼之道》精华分享与讨论(5)——Kernel地图:Kconfig与Makefile
    写出高效优美的单片机C语言代码
    哈夫曼树
    如何提高浮点数变整数的精度
    CF798C Mike and gcd problem
    CF822C Hacker, pack your bags!
    CF821C Okabe and Boxes
  • 原文地址:https://www.cnblogs.com/Achenchen/p/9544332.html
Copyright © 2011-2022 走看看