UVA 804 Petri Net Simulation
题意:对于一个变迁,需要多个入口满足,然后有多个出口。需要判断多次变迁之后是否这个网络还在运行。多个变迁任意进行一个不会对结果产生影响。
感谢:https://github.com/morris821028/UVa/blob/master/volume008/804%20-%20Petri%20Net%20Simulation.cpp
题解:解题思路方向正确思维不难。
但是作为模拟,如果打算从第一个开始往后走那一定是做不出来的。从一开始给的就有可能有多个可以变迁的方向考虑,我们遍历查询能够变迁的即可。
/*
author : mxylulu
date : 2019/2/21
says : 唯有全力以赴。
*/
#include<bits/stdc++.h>
#define FOR(i,a,b) for(int i=a;i<=b;i++)
#define RFOR(i,a,b) for(int i=a;i>=b;i--)
#define sf(i) scanf("%d",&i)
#define pf(i) printf("%d ",i)
using namespace std;
typedef long long LL;
int N,M,T;
int H[200];
vector<int>in[200];
vector<int>out[200];
void remove(int i)
{
FOR(j,0,in[i].size()-1)
{
H[in[i][j]]--;
}
}
void resume(int i)
{
FOR(j,0,in[i].size()-1)
{
H[in[i][j]]++;
}
}
bool check(int i)
{
remove(i);
bool ok=true;
FOR(j,0,in[i].size()-1)
{
if(H[in[i][j]]<0)ok=false;
}
resume(i);
return ok;
}
void action(int i)
{
remove(i);
FOR(j,0,out[i].size()-1)
{
H[out[i][j]]++;
}
}
void simulate()
{
FOR(i,1,T)
{
int update = 0;
FOR(j,1,M)
if(check(j))
{
update = 1;
action(j);
break;
}
if(!update)
{
printf("dead after %d transitions\n",i-1);
return ;
}
}
printf("still live after %d transitions\n",T);
}
int main()
{
int cases = 0;
cin>>N;
while(N!=0)
{
++cases;
FOR(i,1,N)cin>>H[i];
cin>>M;
FOR(i,1,M)in[i].clear(),out[i].clear();
FOR(i,1,M)
{
int temp;
cin>>temp;
while(temp!=0)
{
if(temp<0)in[i].push_back(-temp);
else out[i].push_back(temp);
cin>>temp;
}
}
cin>>T;
printf("Case %d: ",cases);
simulate();
printf("Places with tokens:");
FOR(i,1,N)
if(H[i])printf(" %d (%d)",i,H[i]);
puts("\n");
cin>>N;
}
//system("pause");
return 0;
}