题意:n(1e5)种食物,每种食物有w[i](1e6)个,m(2e5)个朋友,每个朋友有两种喜欢的食物并且每次各吃一盘,安排一种顺序使每个朋友至少能吃到一种喜欢的食物.
贪心,记sum[i]为某种食物的需求总量,若w[i]>=sum[i],则喜欢该食物的朋友至少能吃到一种,将这些朋友的另一种食物需求量各减1,然后就是拓扑模拟这个过程把结果逆序输出
#include<bits/stdc++.h>
using namespace std;
const int maxn = 2e5+7;
int w[maxn],sum[maxn],n,m;
vector<pair<int,int>>node[maxn];
stack<int>ans;
bool vis[maxn];
bool topo()
{
queue<int>q;
for(int i=1;i<=n;i++)
{
if(sum[i]<=w[i])q.push(i);
}
while(!q.empty())
{
int u = q.front();
q.pop();
for(auto it : node [u])
{
if(vis[it.second])continue;
vis[it.second] = true;
ans.push(it.second);
if(--sum[it.first] <= w[it.first])
{
q.push(it.first);
}
}
}
return ans.size() == m;
}
int main()
{
scanf("%d%d",&n,&m);
for(int i=1;i<=n;i++)
scanf("%d",w+i);
for(int i=1;i<=m;i++)
{
int x,y;
scanf("%d%d",&x,&y);
node[x].emplace_back(y,i);
node[y].emplace_back(x,i);
sum[x]++,sum[y]++;
}
if(topo())
{
puts("ALIVE");
while(!ans.empty())
{
printf("%d ",ans.top());
ans.pop();
}
}
else
puts("DEAD");
return 0;
}