zoukankan      html  css  js  c++  java
  • POJ3295Tautology

    转载请注明出处:優YoU  http://user.qzone.qq.com/289065406/blog/1309062835

     

    大致题意:

    输入由pqrstKANCE10个字母组成的逻辑表达式,

    其中pqrst的值为1true)或0false),即逻辑变量;

    KANCE为逻辑运算符,

    K --> and:  x && y

    A --> or:  x || y

    N --> not :  !x

    C --> implies :  (!x)||y

    E --> equals :  x==y

    问这个逻辑表达式是否为永真式。

    PS:输入格式保证是合法的

     

    解题思路:

    p, q, r, s, t不同的取值组合共32种情况,枚举不同取值组合代入逻辑表达式WFF进行计算。

    如果对于所有的取值组合,WFF值都为 true, 则结果为 tautology,否则为 not
      

    WFF的计算方法:

    从字符串WFF的末尾开始依次向前读取字符。

    构造一个栈stack,当遇到逻辑变量 p, q, r, s ,t 则将其当前的值压栈;

    遇到 N 则取栈顶元素进行非运算,运算结果的值压栈;

    遇到K, A, C, E则从栈顶中弹出两个元素进行相应的运算,将结果的值压栈。 

    由于输入是合法的,当字符串WFF扫描结束时,栈stack中只剩一个值,该值就是逻辑表达式WFF的值。

     

     

    栈可以自己构造,也可以利用STL的<stack>,都一样,下面我两种代码都贴出:

     

      1 /*代码一:自己构造栈*/
    2
    3 //Memory Time
    4 //212K 79MS
    5
    6 #include<iostream>
    7 using namespace std;
    8
    9 int pp,qq,rr,ss,tt; //各个逻辑变量的值
    10
    11 typedef class STACK
    12 {
    13 public:
    14 int value;
    15 class STACK* next;
    16 STACK()
    17 {
    18 next=0;
    19 }
    20 }Stack;
    21
    22 typedef class Top
    23 {
    24 public:
    25 Stack* top;
    26 Top()
    27 {
    28 top=0;
    29 }
    30 }linkstack;
    31
    32 void Insert(linkstack* s,int e); //入栈
    33 int Pop(linkstack* s); //栈顶值出栈
    34 void Empty(linkstack* s); //清空栈
    35
    36 bool isvariables(linkstack* s,char ch); //判断ch是否为变量p q r s t,若是则把其当前值入栈
    37 void operators(linkstack* s,char op); //根据操作符op对栈执行操作
    38 int K(int x,int y); //and: x&&y
    39 int A(int x,int y); //or : x||y
    40 int C(int x,int y); //implies: (!x)||y
    41 int E(int x,int y); //equals: x==y
    42 int N(int x); //not: !x
    43
    44 int main(void)
    45 {
    46 linkstack* s=new linkstack[sizeof(linkstack)];
    47
    48 char WFF[110];
    49 while(cin>>WFF && WFF[0]!='0')
    50 {
    51 int len=strlen(WFF); //逻辑表达式的长度
    52
    53 bool flag=true; //标记逻辑表达式是否为永真式
    54 for(pp=0;pp<=1;pp++) //枚举逻辑变量的值
    55 {
    56 for(qq=0;qq<=1;qq++)
    57 {
    58 for(rr=0;rr<=1;rr++)
    59 {
    60 for(ss=0;ss<=1;ss++)
    61 {
    62 for(tt=0;tt<=1;tt++)
    63 {
    64 for(int pw=len-1;pw>=0;pw--)
    65 {
    66 if(!isvariables(s,WFF[pw]))
    67 operators(s,WFF[pw]);
    68 }
    69
    70 int ans=s->top->value; //最后栈剩一个值,即为逻辑表达式的值
    71 if(!ans) //只要表达式有一个值为假,它就不是永真式
    72 {
    73 flag=false;
    74 break;
    75 }
    76 Empty(s);
    77 }
    78 if(!flag)
    79 break;
    80 }
    81 if(!flag)
    82 break;
    83 }
    84 if(!flag)
    85 break;
    86 }
    87 if(!flag)
    88 break;
    89 }
    90 if(flag)
    91 cout<<"tautology"<<endl;
    92 else
    93 cout<<"not"<<endl;
    94 }
    95 return 0;
    96 }
    97
    98 void Insert(linkstack* s,int e)
    99 {
    100 Stack* node=new Stack[sizeof(Stack)];
    101 node->value=e;
    102 node->next=s->top;
    103 s->top=node;
    104
    105 return;
    106 }
    107
    108 int Pop(linkstack* s)
    109 {
    110 int e=s->top->value;
    111 Stack* temp=s->top;
    112 s->top=s->top->next;
    113 delete temp;
    114
    115 return e;
    116 }
    117
    118 void Empty(linkstack* s)
    119 {
    120 while(s->top)
    121 {
    122 Stack* temp=s->top;
    123 s->top=s->top->next;
    124 delete temp;
    125 }
    126 return;
    127 }
    128
    129 bool isvariables(linkstack* s,char ch)
    130 {
    131 switch(ch)
    132 {
    133 case 'p':Insert(s,pp);return true;
    134 case 'q':Insert(s,qq);return true;
    135 case 'r':Insert(s,rr);return true;
    136 case 's':Insert(s,ss);return true;
    137 case 't':Insert(s,tt);return true;
    138 }
    139 return false;
    140 }
    141
    142 void operators(linkstack* s,char op)
    143 {
    144 switch(op)
    145 {
    146 case 'K':
    147 {
    148 int x=Pop(s);
    149 int y=Pop(s);
    150 Insert(s,K(x,y));
    151 break;
    152 }
    153 case 'A':
    154 {
    155 int x=Pop(s);
    156 int y=Pop(s);
    157 Insert(s,A(x,y));
    158 break;
    159 }
    160 case 'C':
    161 {
    162 int x=Pop(s);
    163 int y=Pop(s);
    164 Insert(s,C(x,y));
    165 break;
    166 }
    167 case 'E':
    168 {
    169 int x=Pop(s);
    170 int y=Pop(s);
    171 Insert(s,E(x,y));
    172 break;
    173 }
    174 case 'N':
    175 {
    176 int x=Pop(s);
    177 Insert(s,N(x));
    178 break;
    179 }
    180 }
    181 return;
    182 }
    183
    184 int K(int x,int y)
    185 {
    186 return x&&y;
    187 }
    188
    189 int A(int x,int y)
    190 {
    191 return x||y;
    192 }
    193
    194 int C(int x,int y)
    195 {
    196 return (!x)||y;
    197 }
    198
    199 int E(int x,int y)
    200 {
    201 return x==y;
    202 }
    203
    204 int N(int x)
    205 {
    206 return !x;
    207 }

    ==============华丽的分割线==============

     

      1 /*代码二:STL<stack>*/
    2
    3 //Memory Time
    4 //216K 0MS
    5
    6 #include<iostream>
    7 #include<stack>
    8 using namespace std;
    9
    10 int pp,qq,rr,ss,tt; //各个逻辑变量的值
    11 stack<int> s;
    12
    13 bool isvariables(char ch); //判断ch是否为变量p q r s t,若是则把其当前值入栈
    14 void operators(char op); //根据操作符op对栈执行操作
    15
    16 int main(void)
    17 {
    18 char WFF[110];
    19 while(cin>>WFF && WFF[0]!='0')
    20 {
    21 int len=strlen(WFF); //逻辑表达式的长度
    22
    23 bool flag=true; //标记逻辑表达式是否为永真式
    24 for(pp=0;pp<=1;pp++) //枚举逻辑变量的值
    25 {
    26 for(qq=0;qq<=1;qq++)
    27 {
    28 for(rr=0;rr<=1;rr++)
    29 {
    30 for(ss=0;ss<=1;ss++)
    31 {
    32 for(tt=0;tt<=1;tt++)
    33 {
    34 for(int pw=len-1;pw>=0;pw--)
    35 {
    36 if(!isvariables(WFF[pw]))
    37 operators(WFF[pw]);
    38 }
    39 int ans=s.top(); //最后栈剩一个值,即为逻辑表达式的值
    40 s.pop(); //清空栈
    41 if(!ans) //只要表达式有一个值为假,它就不是永真式
    42 {
    43 flag=false;
    44 break;
    45 }
    46 }
    47 if(!flag)
    48 break;
    49 }
    50 if(!flag)
    51 break;
    52 }
    53 if(!flag)
    54 break;
    55 }
    56 if(!flag)
    57 break;
    58 }
    59 if(flag)
    60 cout<<"tautology"<<endl;
    61 else
    62 cout<<"not"<<endl;
    63 }
    64 return 0;
    65 }
    66
    67 bool isvariables(char ch)
    68 {
    69 switch(ch)
    70 {
    71 case 'p':s.push(pp);return true;
    72 case 'q':s.push(qq);return true;
    73 case 'r':s.push(rr);return true;
    74 case 's':s.push(ss);return true;
    75 case 't':s.push(tt);return true;
    76 }
    77 return false;
    78 }
    79
    80 void operators(char op)
    81 {
    82 switch(op)
    83 {
    84 case 'K':
    85 {
    86 int x=s.top();
    87 s.pop();
    88 int y=s.top();
    89 s.pop();
    90 s.push(x&&y);
    91 break;
    92 }
    93 case 'A':
    94 {
    95 int x=s.top();
    96 s.pop();
    97 int y=s.top();
    98 s.pop();
    99 s.push(x||y);
    100 break;
    101 }
    102 case 'C':
    103 {
    104 int x=s.top();
    105 s.pop();
    106 int y=s.top();
    107 s.pop();
    108 s.push((!x)||y);
    109 break;
    110 }
    111 case 'E':
    112 {
    113 int x=s.top();
    114 s.pop();
    115 int y=s.top();
    116 s.pop();
    117 s.push(x==y);
    118 break;
    119 }
    120 case 'N':
    121 {
    122 int x=s.top();
    123 s.pop();
    124 s.push(!x);
    125 break;
    126 }
    127 }
    128 return;
    129 }

  • 相关阅读:
    Prime Land(poj 1365)
    备用交换机(cogs 8)
    救命(洛谷 U4525)
    消息传递(cogs 1001)
    SQLite 使用主键,ROWID 及自增列
    SqlHelper 类
    一个继承的 DataGridView
    给JAVA的eclipse IDE 在线安装 SVN插件 / 给 eclipse 添加打开所在的文件夹功能
    实时更新DataGridView 合计值
    导出为文本格式
  • 原文地址:https://www.cnblogs.com/lyy289065406/p/2120571.html
Copyright © 2011-2022 走看看