poj 3295 专题第五道

wrong了好多次。。我才发现我把E没注意 以为是异或,其实是判断是否相等。。。。orz

这题应该不能算是自己独立思考出来的,之前有思考过但是因为我是从正序想的所以导致没有什么头绪,,看了下解题报告的思路,说要用stack,刚好小紫书正要学,就先放下了,小紫书学了后,来做这题。当然我是直接用STL里面的orz。。

思路主要就是要利用题目的特性,从后往前读字符串是最直观的,然后对于pqrst来说要枚举每一种情况,用五个循环就行啦。。然后可以使用一个map来进行pqrst与各自对应值的映射。。还有就是利用stack啦,从后往前读并其入栈,然后出栈和运算符进行运算再将运算的结果入栈,像not就只要将一个出栈,而其他的需要将两个元素出栈来进行一系列的运算。。这样一直做到最后一定就会只剩一个在栈内,取出来其值就是整个表达式的值。。。还有就是每组数据结束之后要记得将那个值出栈避免留栈内,否则最后会有很多组的数都留在了栈内。。。万一测试数据超级多可能爆掉。。(虽然我忘了出栈也AC了但是还是规范点好)

附上ac代码:

#include<cstdio>
#include<cstring>
#include<stack>
#include<map>
using namespace std;
char s[150];
map<char,int> ID;
stack<int> WFF;
int scan()
{
	for(int i = strlen(s)-1;i >= 0;i--)
	{
		if(s[i]>='p'&&s[i]<='t')
		 WFF.push(ID[s[i]]);
		else if(s[i] == 'N')
		{
			int x = WFF.top();
			WFF.pop();
			WFF.push(!x);
		}
		else if(s[i] == 'K')
		{
			int x1 = WFF.top();
			WFF.pop();
			int x2 = WFF.top();
			WFF.pop();
			WFF.push(x1&&x2);
		}
		else if(s[i] == 'A')
		{
			int x1 = WFF.top();
			WFF.pop();
			int x2 = WFF.top();
			WFF.pop();
			WFF.push(x1||x2);
		}
		else if(s[i] == 'C')
		{
			int x1 = WFF.top();
			WFF.pop();
			int x2 = WFF.top();
			WFF.pop();
			WFF.push((!x1)||x2);
		}
		else if(s[i] == 'E')
		{
			int x1 = WFF.top();
			WFF.pop();
			int x2 = WFF.top();
			WFF.pop();
			WFF.push(x1==x2);
		}
	}
	return WFF.top();
}
int main ()
{
	while(scanf("%s",s)==1)
	{
		if(s[0]=='0') break;
		int flag=0;
		for(ID['p'] = 0;ID['p'] < 2;ID['p']++)
		for(ID['q'] = 0;ID['q'] < 2;ID['q']++)
		for(ID['r'] = 0;ID['r'] < 2;ID['r']++)
		for(ID['s'] = 0;ID['s'] < 2;ID['s']++)
		for(ID['t'] = 0;ID['t'] < 2;ID['t']++)
		{
			if(!scan())
			{
				flag=1;
				goto out;
			}
		}
		out:
		if(flag) printf("not\n");
		else printf("tautology\n");
		WFF.pop();   //要将栈内的元素弹出来,不要让它留在栈里 
	}
	return 0;
}


你可能感兴趣的:(poj 3295 专题第五道)