牛客题解 | 扑克牌四则运算
题目
题解
题目难度:中等难度
难点分析:
1.对于四个数字具有24种排列方式。比如:1 2 3 4 可以重新排列为1 3 4 2、4 3 2 1等情况。
2.两个数字之间可以插入任意符号“+” 、“-”、“*”、“/”,四个数字一共有3个符号
3.运算符具有优先级,需要先进行“*”、“/”运算,再进行“+”、“-”运算。
知识点:栈、全排列、字典序、四则运算
思路:
首先思考一个运算式子的计算过程:(使用栈)
如 1 + 3 * 5 - 6
其中数字放入数组a种,运算符放入数组b种(1表示“+”,2表示“-”,3表示“*”,4表示“/”)
数组a:
数组b:
第一步:
将a[0]压入栈s中
第二步:
依次判断每个运算符:
如果是“+”和“-”,直接压入栈s中(不能直接运算,需要继续判断之后是否存在“*”“/”优先级更高的运算符)。
如果是“*”、“/”,弹出栈顶元素进行乘或者除操作。
第三步:
在第二步中,所用的乘除运算已经运算完成,现在进行加减运算。由于栈先弹出后压入的数字,同时加减运算满足结合
律,因此对数组b运算符逆序依次判断:
当b[x]=1时:
弹出栈顶两个元素,将相加之和压入栈中
当b[x]=2时:
弹出栈顶两个元素相减,注意:后后弹出元素减先弹出元素
当b[x]=3或者b[x]=4时:
由于第二步已经运算过,直接跳过(代码中,在第二步乘除运算后将b[x]赋值为0,因此当b[x]=0时直接跳过运算即可)。
第四步:
通过第三步运算,栈中比保存一个元素,即为运算结果。
考虑数组a中数组的顺序问题,使用STL对其进行全排列。
STL中有两个关于全排列的函数,分别为next_permutation(下一个排列)和prev_permutation(上一个排列),这两
个算法都是以“字典序”为准则进行全排列的。所谓某一序列的全排列,指的是:“序列上每一位都取完该序列所包含的所
有元素”,如“123”的全排列为:“123”、“132”、“213”、“231”、“312”、“321”,共6种情况。
【注】得到通过next_permutation(下一个排列)函数得到全排列需要先对数字进行排序
关于运算符数组b:
通过三层for循环得到,每层循环代表一个位置的符号,包括四种情况(1表示“+”,2表示“-”,3表示“*”,4表示“/”)
#include<iostream>
#include<stack>
#include<algorithm>
using namespace std;
int main(){
int n=4,m;
stack<int> s;
int a[n];
for(int i=0;i<n;i++){ cin>>a[i];
}
cin>>m;
sort(a,a+4);
do{
for(int i=1;i<=4;i++){
for(int j=1;j<=4;j++){
for(int k=1;k<=4;k++){
s.push(a[0]);
int b[3];
b[0]=i;b[1]=j;b[2]=k;
for(int x=0;x<3;x++){
if(b[x]==1||b[x]==2) s.push(a[x+1]);
else{
int tmp=s.top();
s.pop();
if(b[x]==3) s.push(tmp*a[x+1]);
else s.push(tmp/a[x+1]);
b[x]=0;
}
}
for(int x=2;x>=0;x--){
if(b[x]==0) continue;
else if(b[x]==1) {
int tmp;
tmp=s.top();
s.pop();
tmp+=s.top();
s.pop();
s.push(tmp);
}else{
int tmp;
tmp=s.top();
s.pop();
tmp=s.top()-tmp;
s.pop();
s.push(tmp);
}
}
// cout<</n;i++){></int></algorithm></stack></iostream>

浙公网安备 33010602011771号