zoukankan      html  css  js  c++  java
  • POJ 2749

    二分+2SAT的题

    写错了HIGH和LOW与MID的变换,TLE了好几次。。

    按HATE和LIKE关系先加边,再用距离的限制加边。

    dist(i,S1)+dist(S1,j)>limit  Xi->~Xj  Xj->Xi

    dist(i,S2)+dist(S2,j)>limit  ~Xi->Xj  ~Xj->Xi

    dist(i,S1)+dist(S1,S2)+dist(S2,j)>limit Xi->Xj  ~Xj->~Xi

    dist(i,S2)+dist(S2,S1)+dist(S1,j)>limit ~Xi->~Xj  Xj->Xi

    用离散数学的知识就能推出来,以上借别人的一用。

      1 #include <iostream>
      2 #include <cstdio>
      3 #include <cstring>
      4 #include <algorithm>
      5 #include <cmath>
      6 
      7 using namespace std;
      8 
      9 const int inf=8500000;
     10 const int MAXN=1050;
     11 const int MAXM=20000000;
     12 int s1_s2,dis1[MAXN],dis2[MAXN],head[MAXN],dfn[MAXN],low[MAXN],belong[MAXN];
     13 int st[MAXN],stop,indx,tot,pat;
     14 bool stack[MAXN]; int leng;
     15 int n,hn,ln;
     16 struct d{
     17     int x,y;
     18 }point[MAXN],s1,s2;
     19 struct h{
     20     int u,v;
     21 }hate[MAXN*2];
     22 struct l{
     23     int u,v;
     24 }like[MAXN*2];
     25 
     26 struct ei{
     27     int u,v;
     28     int next;
     29 }edge[MAXM];
     30 
     31 void addedge(int u,int v){
     32     edge[tot].u=u;
     33     edge[tot].v=v;
     34     edge[tot].next=head[u];
     35     head[u]=tot++;
     36 }
     37 
     38 void tarjan(int u){
     39     int v;
     40     dfn[u]=low[u]=++indx;
     41     st[stop++]=u;
     42     stack[u]=true;
     43     for(int e=head[u];e!=-1;e=edge[e].next){
     44         v=edge[e].v;
     45         if(dfn[v]==0){
     46             tarjan(v);
     47             low[u]=min(low[u],low[v]);
     48         }
     49         else if(stack[v]){
     50             low[u]=min(low[u],dfn[v]);
     51         }
     52     }
     53     if(dfn[u]==low[u]){
     54         pat++;
     55         do{
     56             v=st[--stop];
     57             stack[v]=false;
     58             belong[v]=pat;
     59         }while(u!=v);
     60     }
     61 }
     62 
     63 bool slove(){
     64     int u,v;
     65     
     66     memset(head,-1,sizeof(head));
     67     memset(dfn,0,sizeof(dfn));
     68     memset(low,0,sizeof(low));
     69     memset(belong,0,sizeof(belong));
     70     stop=0; indx=0; tot=0; pat=0;
     71     memset(stack,false,sizeof(stack));
     72     
     73     
     74     for(int i=0;i<hn;i++){
     75         u=hate[i].u;
     76         v=hate[i].v;
     77         addedge(u*2,v*2+1);
     78         addedge(v*2,u*2+1);
     79         addedge(2*u+1,2*v);
     80         addedge(2*v+1,2*u);
     81     }
     82     for(int i=0;i<ln;i++){
     83         u=like[i].u;
     84         v=like[i].v;
     85         addedge(u*2,v*2);
     86         addedge(v*2,u*2);
     87         addedge(2*u+1,2*v+1);
     88         addedge(2*v+1,2*u+1);
     89     }
     90     for(int i=0;i<n;i++){
     91         for(int j=i+1;j<n;j++){
     92             if(dis1[i]+dis1[j]>leng){
     93                 addedge(i*2,j*2+1);
     94                 addedge(j*2,i*2+1);
     95             }
     96             if(dis2[i]+dis2[j]>leng){
     97                 addedge(i*2+1,j*2);
     98                 addedge(j*2+1,i*2);
     99             }
    100             if(dis1[i]+s1_s2+dis2[j]>leng){
    101                 addedge(i*2,j*2);
    102                 addedge(j*2+1,i*2+1);
    103             }
    104             if(dis2[i]+s1_s2+dis1[j]>leng){
    105                 addedge(j*2,i*2);
    106                 addedge(i*2+1,j*2+1);
    107             }
    108         }
    109     }
    110     for(int i=0;i<2*n;i++){
    111         if(dfn[i]==0)
    112         tarjan(i);
    113     }
    114     bool flag=true;
    115     for(int i=0;i<n;i++){
    116         if(belong[2*i]==belong[2*i+1]){
    117             flag=false;
    118             break;
    119         }
    120     }
    121     return flag;
    122 }
    123 
    124 int main(){
    125     int u,v; int tmp;
    126     while(scanf("%d%d%d",&n,&hn,&ln)!=EOF){
    127         scanf("%d%d%d%d",&s1.x,&s1.y,&s2.x,&s2.y);
    128         for(int i=0;i<n;i++){
    129         scanf("%d%d",&point[i].x,&point[i].y);
    130         }
    131         for(int i=0;i<hn;i++){
    132             scanf("%d%d",&u,&v);
    133             u--; v--;
    134             hate[i].u=u; hate[i].v=v;
    135         }
    136         for(int i=0;i<ln;i++){
    137             scanf("%d%d",&u,&v);
    138             u--; v--; 
    139             like[i].u=u; like[i].v=v;
    140         }
    141         for(int i=0;i<n;i++){
    142             tmp=abs(point[i].x-s1.x)+abs(point[i].y-s1.y);
    143             dis1[i]=tmp;
    144             tmp=abs(point[i].x-s2.x)+abs(point[i].y-s2.y);
    145             dis2[i]=tmp;
    146         }
    147         s1_s2=abs(s1.x-s2.x)+abs(s1.y-s2.y);
    148         int lown=1,high=inf,ans=-1;
    149         while(lown<=high){
    150             int mid=(lown+high)/2;
    151             leng=mid;
    152             if(slove()){
    153                 ans=mid;
    154                 high=mid-1;
    155             }
    156             else lown=mid+1;
    157         }
    158         printf("%d
    ",ans);
    159     }
    160     return 0;
    161 }
    View Code
  • 相关阅读:
    Eclipse(MyEclipse)使用技巧——改动凝视字体大小
    C++标准库之 Lower_Bound, upper_Bound
    Mongodb地理空间索引
    AfxMessageBox和MessageBox差别
    具体解释VB中连接access数据库的几种方法
    C++中this指针的使用方法.
    秒杀多线程第四篇 一个经典的多线程同步问题
    设计模式学习03—抽象工厂模式
    Neutron中的Service类
    Opencv学习笔记(六)SURF学习笔记
  • 原文地址:https://www.cnblogs.com/jie-dcai/p/3856072.html
Copyright © 2011-2022 走看看