Tautology POJ 3295

本文介绍了一种名为WFF'nProof的逻辑游戏,玩家通过骰子上的符号组合成逻辑公式,并判断这些公式是否为恒真式。文章详细解释了游戏规则及逻辑运算符的定义,并提供了一个算法示例来解决这一问题。

题目:

WFF 'N PROOF is a logic game played with dice. Each die has six faces representing some subset of the possible symbols K, A, N, C, E, p, q, r, s, t. A Well-formed formula (WFF) is any string of these symbols obeying the following rules:

  • p, q, r, s, and t are WFFs
  • if w is a WFF, Nw is a WFF
  • if w and x are WFFs, Kwx, Awx, Cwx, and Ewx are WFFs.
The meaning of a WFF is defined as follows:
  • p, q, r, s, and t are logical variables that may take on the value 0 (false) or 1 (true).
  • K, A, N, C, E mean and, or, not, implies, and equals as defined in the truth table below.
Definitions of K, A, N, C, and E
     w  x  Kwx  Awx   Nw  Cwx  Ewx
  1  1  1  1   0  1  1
  1  0  0  1   0  0  0
  0  1  0  1   1  1  0
  0  0  0  0   1  1  1

tautology is a WFF that has value 1 (true) regardless of the values of its variables. For example, ApNp is a tautology because it is true regardless of the value of p. On the other hand, ApNq is not, because it has the value 0 for p=0, q=1.

You must determine whether or not a WFF is a tautology.

Input

Input consists of several test cases. Each test case is a single line containing a WFF with no more than 100 symbols. A line containing 0 follows the last case.

Output

For each test case, output a line containing tautology or not as appropriate.

Sample Input

ApNp
ApNq
0

Sample Output

tautology
not


#include<iostream>
#include<stdio.h>
#include<stack>
#include<string.h>
using namespace std;
stack<int> digit;
int len;
char temp[110];
// p, q, r, s, t
int d[6];
bool isOpe(char c){  //K, A, N, C, E
    if('K'==c||'A'==c||'N'==c||'C'==c||'E'==c) return true;
    return false;
}
bool solve(){
    int i;
    int op1,op2;
    for(i=len-1;i>=0;i--){
//        cout<<"i="<<i<<" ->"<<temp[i]<<endl;
        if(isOpe(temp[i])){ //如果是操作符,进行运算
            switch(temp[i]){
            case 'K':{
                op2=digit.top();
                digit.pop();
                op1=digit.top();
                digit.pop();
                if(op1&&op2) digit.push(1);
                else digit.push(0);
                break;
            }
            case 'A':{
                op2=digit.top();
                digit.pop();
                op1=digit.top();
                digit.pop();
                if(op1||op2) digit.push(1);
                else digit.push(0);
                break;
            }
            case 'N':{
                op1=digit.top();
                digit.pop();
                if(op1) digit.push(0);
                else digit.push(1);
                break;
            }
            case 'C':{
                op1=digit.top();
                digit.pop();
                op2=digit.top();
                digit.pop();
                if(op1==1&&op2==0) digit.push(0);
                else digit.push(1);
                break;
            }
            case 'E':{
                op2=digit.top();
                digit.pop();
                op1=digit.top();
                digit.pop();
                if(op1==op2) digit.push(1);
                else digit.push(0);
                break;
            }
        }
        }else{
            switch(temp[i]){
            case 'p':
                digit.push(d[0]);
                break;
            case 'q':
                digit.push(d[1]);
                break;
            case 'r':
                digit.push(d[2]);
                break;
            case 's':
                digit.push(d[3]);
                break;
            case 't':
                digit.push(d[4]);
                break;
            }
        }
    }
    int ans=digit.top();
    if(ans) return true;
    return false;
}
bool change(){
    d[0]++;
    int i;
    i=0;
    while(i<5){
        if(d[i]>=2){
            d[i+1]++;
            d[i]-=2;
        }
        i++;
    }
    if(d[5]) return true;
    return false;
}
int main(){
    while(scanf("%s",temp),temp[0]!='0'){
        len=strlen(temp);
//        printf("%s %d\n",temp,len);
        while(!digit.empty()){
            digit.pop();
        }
        memset(d,0,sizeof(d));
        bool res;
        while(1){
            res=solve();
            if(!res) break;
            if(change()) break;
        }
        if(res) printf("tautology\n");
        else printf("not\n");
    }
    return 0;
}

实现时使用堆栈,简化操作。注意每个运算符操作的是右边离他最近的2个数,不要把操作数和操作符分开存储,之前写的代码是把操作数和操作符分开,导致代码出错。

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值