hdu 3622 Bomb Game(二分答案+2-sat判斷答案可行性)
題目連結:
題目大意:
有n個炸彈,每個炸彈的放置位置有兩個可選,每個炸彈的爆炸範圍不能交叉,問我所有炸彈的中爆炸範圍最小的那個炸彈的爆炸範圍最大是多少
題目分析:
首先炸彈放置的位置是兩個,那麼就是2-sat問題,我們只需要二分答案,然後判斷答案是否合法,如果答案合法,那麼答案就可能是更大的值,每次二分出的mid值作為所有炸彈的爆炸範圍,如果他們能夠得到不會交叉的解,那麼說明當前方案可行,建邊的時候就是對於任意兩個點,列舉他們各自的兩個點是否會相交,如果會,那麼選其中一個就一定不選另一個
程式碼如下:
#include <iostream> #include <cstring> #include <cstdio> #include <algorithm> #include <vector> #include <stack> #include <cmath> #define MAX 207 #define eps 1e-9 using namespace std; int mark[MAX],dfn[MAX],low[MAX],belong[MAX],times,cnt; vector<int> e[MAX]; stack<int> s; struct Point { double x,y; }p[MAX]; double dis ( Point a , Point b ) { return sqrt ((a.x-b.x)*(a.x-b.x) + (a.y-b.y)*(a.y-b.y)); } void tarjan ( int u ) { dfn[u] = low[u] = ++times; mark[u] = 1; s.push ( u ); int len = e[u].size(); for ( int i= 0 ; i < len ; i++ ) { int v = e[u][i]; if ( !mark[v] ) { tarjan ( v ); low[u] = min ( low[u] , low[v] ); } if ( mark[v] == 1 ) low[u] = min ( low[u] , dfn[v] ); } if ( dfn[u] == low[u] ) { int temp; do { temp = s.top(); belong[temp] = cnt; mark[temp] = 2; s.pop(); }while ( temp != u ); cnt++; } } void init ( ) { memset ( mark , 0 , sizeof ( mark )); for ( int i = 0 ; i < MAX ; i++ ) e[i].clear(); while ( !s.empty() ) s.pop(); times = cnt = 0; } int n,m; bool check ( double mid ) { init(); for ( int i = 0 ; i < n ; i++ ) for ( int j = i+1 ; j < n ; j++ ) { int x = i<<1 , y = j<<1; int u = i<<1|1 , v = j<<1|1; /*if ( dis( p[x] , p[y] ) + eps < mid && dis ( p[u] , p[v] ) + eps < mid dis( p[u] , p[y] ) + eps < mid && dis ( p[x] , p[v] ) + eps < mid ) return false;*/ if ( dis ( p[x] , p[y] ) + eps < mid*2 ) { e[x].push_back( v ); e[y].push_back( u ); } if ( dis ( p[u] , p[v] ) + eps < mid*2 ) { e[u].push_back ( y ); e[v].push_back ( x ); } if ( dis ( p[x] , p[v]) + eps < mid*2 ) { e[x].push_back ( y ); e[v].push_back ( u ); } if ( dis ( p[u] , p[y] ) + eps < mid*2 ) { e[u].push_back ( v ); e[y].push_back ( x ); } } for ( int i = 0 ; i < 2*n ; i++ ) if ( !mark[i] ) tarjan ( i ); for ( int i = 0 ; i < n ; i++ ) if ( belong[i<<1] == belong[i<<1|1] ) return false; return true; } int main ( ) { while ( ~scanf ( "%d" , &n )) { for ( int i = 0 ; i < n ; i++ ) scanf ( "%lf%lf%lf%lf" , &p[i<<1].x , &p[i<<1].y , &p[i<<1|1].x , &p[i<<1|1].y ); //cout << "YES" << endl; double l = 0 , r = 10000.0, mid; int times = 100; while ( times-- ) { mid = ( l + r )/2.0; if ( check ( mid ) ) l = mid; else r = mid; } printf ( "%.2lf\n" , l ); } }
相關推薦
hdu 3622 Bomb Game(二分答案+2-sat判斷答案可行性)
題目連結: 題目大意: 有n個炸彈,每個炸彈的放置位置有兩個可選,每個炸彈的爆炸範圍不能交叉,問我所有炸彈的中爆炸範圍最小的那個炸彈的爆炸範圍最大是多少 題目分析: 首先炸彈放置的位置是兩個,那麼就是2-sat問題,我們只需要二分答案,然後判斷答案是否合法,如果答案合法,
HDU 3622 Bomb Game【2-SAT 問題】
題目大意:有N對點,給定這N對點的座標,現在要求找出一個最大的半徑R,使得可以從每對點中選擇一個點,並且這N個點以自己為圓心,半徑為R的圓兩兩不相交。 2-SAT問題解法:對於每一對點,我們且稱之為“兄弟點”;對於這2*N個點,如果兩個點之間“矛盾
HDU 3622 Bomb Game
題意:給你n個炸彈,每個炸彈都有兩個位置放置,問你最大的爆炸半徑,使得任意兩個炸彈的爆炸範圍不相交,可以相切,問半徑是多少 思路:對半徑進行二分,很顯然是單調的,所以滿足條件,然後由於點數不是很多,每次n2暴力建圖跑sat 程式碼:(忘記跑tarjan對著空氣debug半小時) #include
BZOJ4078 WF2014Metal Processing Plant(二分答案+2-SAT)
題面甚至沒給範圍,由資料可得n<=200。容易想到二分答案,暴力列舉某集合的價值,2-SATcheck一下即可。這樣是O(n4logn)的。 2-SAT複雜度已經是下界,考慮如何優化列舉。稍微改一下,不妨從大到小列舉較大的集合價值(即列舉邊),另一個集合二分答案,同樣O(n4logn)。
HDU 4115 Eliminate the Conflict(2-sat)
not sof push space clear sans edi ali rgb HDU 4115 Eliminate the Conflict pid=41
Codeforces Round #400 (Div. 1 + Div. 2, combined) D. The Door Problem(二分染色?/2-sat,好題)
Moriarty has trapped n people in n distinct rooms in a hotel. Some rooms are locked, others are unlocked. But, there is a condition that the people in t
POJ 2749 Building roads 2-sat+二分答案
add set color head mem 多少 char size cto 把愛恨和最大距離視為限制條件,可以知道,最大距離和限制條件多少具有單調性 所以可以二分最大距離,加邊+check 1 #include<cstdio> 2 #include
2-Sat+二分_HDU 3622
題目意思是有n個選擇,每次都是隻能在兩個座標中選擇一個,然後再選擇的座標上畫圓,圓不能有重疊部分,問題畫的做大的面積是多少題中是兩個座標選一個,然後約束條件就是在當前半徑下兩個點畫圓是否有重疊,所以這是一個2-Sat問題,但是我們的半徑應該怎麼確定呢?很容易想打二分列舉就好#
HDU 1824 Let's go home (2-SAT判定)
記錄 arch 對數 ref ise stack top code any Let‘s go home Time Limit: 10000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Othe
UVALive3211- Now or later(二分+2-SAT)
print target gin ros 16px ng- arc can 變量 題目鏈接 題意:有n架飛機。每架飛機都能夠選擇早著陸和晚著陸兩種方式之中的一個,且必須選擇一種。任務就是安排全部飛機著陸時。相鄰兩個著陸時間間隔的最小值
HDU 3722 Card Game(二分圖最佳完美匹配+KM算法)
思路 計算 pan style class hdu %d lan har 題目鏈接: http://acm.hdu.edu.cn/showproblem.php?pid=3722 1 /* 2 問題 3 將任意的兩個字符串進行匹配,使得匹配後權值和最大
poj2723 Get Luffy Out解題報告tarjan+2-SAT+二分
fine pan tor build push 若是 註意 ios ack 今天看到講2-SAT比較好的blog,感覺微微的理解了2-SAT 傳送門 參考: https://blog.csdn.net/leolin_/article/details/6680144 題意:你
HDU - 5884 Sort (二分答案+貪心)
sca 優先 scan n) empty 每次 都是 scanf light 有n個數字,你需要把這n個數字合成一個數字,每次只能把k個數字合並成一個,花費為這k個數字的和。 給一個最大花費,問不超過這個最大花費的情況下,k的最小值。 Sample Input 1
Get Luffy Out * HDU - 1816(2 - sat 媽的 智障)
freopen esp names clock int amp min pre ace 題意: 英語限制了我的行動力。。。。就是兩個鑰匙不能同時用,兩個鎖至少開一個 建個圖 二分就好了。。。emm。。。。dfs 開頭low 寫成sccno 然後生活失去希望。。。
Eliminate the Conflict HDU - 4115(2-sat 建圖 hhh)
ems clock memset void cloc define str mat sin 題意: 石頭剪刀布 分別為1、2、3,有n輪,給出了小A這n輪出什麽,然後m行,每行三個數a b k,如果k為0 表示小B必須在第a輪和第b輪的策略一樣,如果k為1 表示小B在第
HDU 1814 2-sat
Peaceful Commission Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 5912 
hdu-1814(2-sat)
dfs div true max 方案 ostream ack %d ems 題意:給你n個組,m條規則,每組有倆個人,這兩個人不能同時出現,然後m條規則代表著有兩個人,這兩個人也不能同時出現,問你是否存在每組都能出現一人的選擇方案 解題思路:因為這個需要字典序輸出,所以只
hdu 3062 (2-sat)
Description 有n對夫妻被邀請參加一個聚會,因為場地的問題,每對夫妻中只有1人可以列席。在2n 個人中,某些人之間有著很大的矛盾(當然夫妻之間是沒有矛盾的),有矛盾的2個人是不會同時出現在聚會上的。有沒有可能會有n 個人同時列席?
hdu 3062 Party【2-Sat】【經典入門】
Party Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 8219 Accepted Submiss
Codeforces Round #378 (Div. 2) D題(二分答案,貪心判斷)
#include <cstdio> #include <cstring> #include <iostream> #include <algorithm>