HDU 5934 Bomb (強連通分量縮點)

2021-09-25 01:14:11 字數 1229 閱讀 4799

【題解】

題意:有n個炸彈,每個炸彈具有三個屬性值:座標(x,y)引爆半徑r以及引爆成本c。當引爆一枚炸彈時,這枚炸彈會同時引爆其**半徑內的所有炸彈,問引爆所有炸彈的最小成本。

思路:乙個炸彈引爆另乙個炸彈可以看做是一條有向邊,那麼所有炸彈的引爆關係就是乙個有向圖。對於有向圖只要引爆入度為0的點就可以將整個炸彈圖全部引爆,也就是最小成本。但是當有向圖成環的時候,這個環沒有乙個入度為0的點,但是需要引爆環中任意一點才可以引爆所有炸彈。因此,我們需要對有向圖進行強連通分量縮點,再將所有入度為0的點的成本相加。

【**】

#includeusing namespace std;

#define maxn 1005

#define maxm 1000005

#define inf 0x3f3f3f3f

#define ll long long

#define mem(a,b) memset(a,b,sizeof(a))

int ea=1;

struct nodef[maxn];

ll cost[maxn];

struct edgeedge[maxm];

int n,cnt,head[maxn];

int low[maxn],dfn[maxn],stack[maxn],belong[maxn],in[maxn];

bool instack[maxn];

int index,top,scc;

int num[maxn];

void add(int u,int v) //建有向邊

void tarjan(int u) //強連通圖縮點

else if(instack[v]&&low[u]>dfn[v])low[u]=dfn[v];

}if(low[u]==dfn[u])while(v!=u);

}}void solve()

int main()

//判斷i是否能引爆j

for(int i=1;i<=n;i++)

}solve();

for(int i=1;i<=n;i++)}}

ll ans=0;

for(int i=1;i<=scc;i++)

if(!in[i])

ans+=cost[i];

printf("case #%d: %lld\n",k,ans);

}return 0;

}

HDU5934 Bomb(強連通分量分解)

題意 給出n個炸彈座標 範圍 費用,如果某乙個炸彈在另乙個炸彈的 範圍內 上 那麼該炸彈也能 問引爆所有炸彈最小的費用 思路 強連通分量分解,將所有點縮點,然後引爆所有入度為0的點即為最小費用 include include include includetypedef long long ll c...

HDU 5934 Bomb 強連通分量縮點

題意 n個炸彈都有乙個座標乙個 半徑以及乙個引爆花費,如果乙個炸彈在另乙個炸彈的 範圍內,則引爆另乙個炸彈,可以導致當前炸彈也 如果當前炸彈的 範圍有其它未炸的炸彈,那麼也能導致這些炸彈 以此聯動。思路 如果i炸彈的 範圍內有j炸彈,則建有向邊i j,然後縮一下點,每個強連通分量內只要引爆乙個,其它...

HDU 5934 Bomb(強連通分量縮點)

題目 顯然可以想到引爆花費最小需要選擇能引爆盡量多的,如果a能引爆b,b能引爆c,一定是引爆a最優。如果有一些點可以相互引爆,那麼就引爆這些點裡花費最小的。能互相引爆 這顯然是乙個強連通分量,因此用tarjan求強連通分量之後,對於每個拓撲序最開頭 入度為0 的連通分量,選擇花費最小的進行引爆,即可...