POJ 2240题(Bellman-Ford)
//解题思路:类似于POJ1860题,是Bellman-Ford算法的变形
#include <iostream>
#include <map>
#include <string>
using namespace std;
#define arraysize 10000 //边值数组开得大一些,否则会出现RE错误
typedef struct node
{
int ci;
int cj;
double rij;
}node;
node edges[arraysize]; //存储边的数组
double d[arraysize]; //存贮兑换成的货币
map<string,int> currencyName; //使用map实现货币名和货币编号的对应
int edgenum;
bool Bellman()
{
memset(d,0,sizeof(d)); //memset同样可以对double类型进行初始化
d[1] = 1; //原货币定义为1
bool final = true;
while(d[1]<=1)
{
final = true; //用于判断是否还可进行松弛操作
for(int i=1;i<edgenum+1;++i) //遍历每条边,并进行松弛操作
{
if(d[edges[i].cj]<d[edges[i].ci]*edges[i].rij)
{
d[edges[i].cj] = d[edges[i].ci]*edges[i].rij;
final = false;
}
}
if(final)
{
break;
}
}
return (d[1]>1); //判断经过松弛操作后,原货币是否增加
}
int main()
{
//freopen("1.txt","r",stdin);
int n;
int m;
int testcase = 0;
while(cin>>n)
{
if(n==0)
break;
testcase++;
edgenum = 0;
string curstr;
string ci;
string cj;
double rij;
for(int i=1;i<n+1;++i)
{
cin>>curstr;
currencyName[curstr] = i; //map
}
cin>>m;
for(int i1=0;i1<m;++i1)
{
edgenum++;
cin>>ci>>rij>>cj;
edges[edgenum].ci = currencyName[ci];
edges[edgenum].rij = rij;
edges[edgenum].cj = currencyName[cj];
}
if(Bellman())
{
printf("Case %d: Yes\n",testcase);
}
else
printf("Case %d: No\n",testcase);
currencyName.clear(); //还要注意,map一次完成之后要清空啊
}
return 0;
}