zoukankan      html  css  js  c++  java
  • CF85E Guard Towers(二分答案+二分图)

    题意

    已知 N 座塔的坐标,N≤5000
    把它们分成两组,使得同组内的两座塔的曼哈顿距离最大值最小
    在此前提下求出有多少种分组方案 mod 109+7

    题解

    二分答案 mid
    曼哈顿距离 >mid 的点连边
    判定是否构成二分图
    方案数为 2^最终的二分图连通块数目
     1 #include<iostream>
     2 #include<cstdio>
     3 #include<algorithm>
     4 #include<cstring>
     5 #include<cmath>
     6 #include<queue>
     7 using namespace std;
     8 const int N=5110;
     9 const int mod=1000000007;
    10 int dis[N][N],n,x[N],y[N],c[N],ans,num; 
    11 long long ksm(long long a,long long x){
    12     long long ans=1;
    13     while(x){
    14         if(x&1){
    15             ans=(ans*a)%mod;
    16         }
    17         x>>=1;
    18         a=(a*a)%mod;
    19     }
    20     return ans;
    21 }
    22 bool dfs(int u,int x,int col){
    23     for(int i=1;i<=n;i++){
    24         if(dis[u][i]>x){
    25             if(c[i]!=-1){
    26                 if(c[i]==col^1)continue;
    27                 if(c[i]==col) return true;
    28             }
    29             c[i]=col^1;
    30             if(dfs(i,x,col^1))return true;
    31         }
    32     }
    33     return false;
    34 }
    35 bool check(int x){
    36 //    cout<<x<<"jsdfhjsdf"<<endl;
    37     memset(c,-1,sizeof(c));
    38     for(int i=1;i<=n;i++){
    39         if(c[i]==-1){
    40             c[i]=1;
    41             if(dfs(i,x,1))return false;
    42         }
    43     }
    44 //    cout<<x<<endl;
    45 //    for(int i=1;i<=n;i++){
    46 //        cout<<c[i]<<" ";
    47 //    }
    48 //    cout<<endl;
    49     return true;
    50 }
    51 void bfs(int u,int col){
    52     queue<int> q;
    53     c[u]=col;
    54     q.push(u);
    55     while(!q.empty()){
    56         int u=q.front();
    57         q.pop();
    58         for(int i=1;i<=n;i++){
    59             if(c[i])continue;
    60             if(dis[i][u]>ans)c[i]=col,q.push(i);
    61         }
    62     } 
    63 }
    64 int main(){
    65     scanf("%d",&n);
    66     for(int i=1;i<=n;i++){
    67         scanf("%d%d",&x[i],&y[i]);
    68     }
    69     for(int i=1;i<=n;i++)    
    70         for(int j=1;j<=n;j++){
    71             dis[i][j]=abs(x[i]-x[j])+abs(y[i]-y[j]);
    72 //            cout<<i<<" "<<j<<" "<<dis[i][j]<<endl; 
    73         } 
    74     int l=0,r=10001;
    75     while(l<=r){
    76         int mid=(l+r)>>1;
    77         if(check(mid)){
    78             ans=mid;
    79             r=mid-1;
    80         }
    81         else l=mid+1;
    82     }
    83     printf("%d
    ",ans);
    84     memset(c,0,sizeof(c));
    85     for(int i=1;i<=n;i++){
    86         if(c[i]==0){
    87             bfs(i,++num);
    88         }
    89     }
    90     printf("%lld",ksm(2,num));
    91 }
    View Code
  • 相关阅读:
    解决virtualbox与mac文件拖拽问题
    SNMP收集
    scapy的安装
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    subprocess.call(cmd, shell=True)
    能够把意见说的让人接受是个技能
    (转)Jenkins2.0 Pipeline 插件执行持续集成发布流程
    ansible 与 Jinja2的结合 -- 安装zabbix
    运维自动化平台-背后的设计计划和架构
    命令行获取zabbix最新的issues
  • 原文地址:https://www.cnblogs.com/Xu-daxia/p/9385907.html
Copyright © 2011-2022 走看看