题意:
模拟程序型计算器,依次输入指令,可能包含的指令有
1. 数字:'NUM X',X为一个只包含大写字母和数字的字符串,表示一个当前进制的数
2. 运算指令:'ADD','SUB','MUL','DIV','MOD',分别表示加减乘,除法取商,除法取余
3. 进制转换指令:'CHANGE K',将当前进制转换为K进制(2≤K≤36)
4. 输出指令:'EQUAL',以当前进制输出结果
5. 重置指令:'CLEAR',清除当前数字
指令按照以下规则给出:
数字,运算指令不会连续给出,进制转换指令,输出指令,重置指令有可能连续给出
运算指令后出现的第一个数字,表示参与运算的数字。且在该运算指令和该数字中间不会出现运算指令和输出指令
重置指令后出现的第一个数字,表示基础值。且在重置指令和第一个数字中间不会出现运算指令和输出指令
进制转换指令可能出现在任何地方
运算过程中中间变量均为非负整数,且小于2^63。
以大写的'A'~'Z'表示10~35
代码:https://blog.csdn.net/Dog_dream/article/details/88181923
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
string toAns(ll n,int ne){
if(n==0) return "0";
string str;
while(n){ //想想10进制转2进制 短除法 n进制的a转m进制的b a模m加到答案上,a除以m 因为a是十进制 比较容易算
int tm=n%ne;
if(tm<=9) str+='0'+tm;
else str+='A'+tm-10;
n/=ne;
}
reverse(str.begin(),str.end());
return str;
}
ll toTen(string str,int ne){
ll ans=0,arg=1;
for(int i=str.size()-1;i>=0;--i){//想想2进制转10进制
if(str[i]<='9') ans+=(str[i]-'0')*arg;
else ans+=(str[i]-'A'+10)*arg;
arg*=ne;
}
return ans;
}
ll getOp(ll a,ll b,string op){
if(op=="ADD") return a+b;
else if(op=="SUB") return a-b;
else if(op=="MUL") return a*b;
else if(op=="DIV") return a/b;
else return a%b;
}
int main(){
int n;
cin>>n;
ll ans=0;
int ne=10;
string str,op;
while(n--){
cin>>str;
if(str=="CLEAR") {str.clear();op.clear();}
else if(str=="EQUAL") {op.clear();cout<<toAns(ans,ne)<<endl;}
else if(str=="CHANGE") {cin>>ne;}
else if(str=="NUM"&&op.empty()){cin>>str;ans=toTen(str,ne);}
else if(str=="NUM"&&!op.empty()){cin>>str;ans=getOp(ans,toTen(str,ne),op);}
else {op=str;} //把+-*/%都放到这个最后的else里
}
return 0;
}
PS:我的30分代码,不知道哪错了...... 先放一放吧(上面的AC代码 人家写的确实思路清晰简洁有序啊)
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
char s1[105],s2[105];
int t[105],a[105];
ll num[2],ans;
//WA1:如果没有op,ans=num[0] 即便没有进行运算,也可能直接输出第1个数
void change(int n,int m){//n转m
int i,k,len=strlen(s1);
for(i=0;i<len;++i) t[len-1-i]=s1[i]-(s1[i]<65?48:s1[i]<97?55:61);
for(k=0;len;){
for(i=len;i>0;--i){
t[i-1]+=t[i]%m*n;//+=
t[i]/=m;
}
a[k++]=t[0]%m;
t[0]/=m;
while(len&&!t[len-1]) --len;
}
s2[k]=0;
for(int i=0;i<k;++i) s2[k-1-i]=a[i]+(a[i]<10?48:a[i]<36?55:61);
}
int main(){
int T;
scanf("%d",&T);
bool flag=0;
int k=10;
string op,opp;
while(T--){
cin>>op;
if(op=="CLEAR"){
flag=0;
ans=0;
s1[0]=0;
num[0]=num[1]=0;
}else if(op=="NUM"){
scanf("%s",s1);
if(k!=10) change(k,10);
else strcpy(s2,s1);
for(int i=0;s2[i];++i){
num[flag]=num[flag]*10+s2[i]-'0';
}
//cout<<"num flag="<<flag<<endl;
//cout<<"num:"<<num[0]<<" "<<num[1]<<"\n";
if(flag){
//cout<<"num:"<<num[0]<<" "<<num[1]<<"\n";
if(opp=="ADD") {ans=num[0]+num[1];}
if(opp=="SUB") {ans=num[0]-num[1];}
if(opp=="MUL") {ans=num[0]*num[1];}
if(opp=="DIV") {ans=num[0]/num[1];}
if(opp=="MOD") {ans=num[0]%num[1];}
num[0]=ans;num[1]=0;
}else ans=num[0];
}else if(op=="CHANGE"){
scanf("%d",&k);
}else if(op=="EQUAL"){
int i=0;
char tmp[105];
while(ans){
tmp[i++]=ans%10+48;
ans/=10;
}
int len=i;
for(i=0;i<len;++i) {
s1[len-1-i]=tmp[i];
//cout<<s1[i];
}
s1[len]=0;
change(10,k);
printf("%s\n",s2);
flag=0;
}else{
opp=op;
flag=1;
}
}
}
改了一下,AC了,所以是在进制转换后的处理出了错,接口没处理好
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
//WA1:如果没有op,ans=num[0] 即便没有进行运算,也可能直接输出第1个数
string toAns(ll n,int k){//10转k
if(!n) return "0";//0要特判哦!!! 不然你返回空串?
string ans;
while(n){
if(n%k<10) ans+='0'+n%k;
else ans+='A'+n%k-10;
n/=k; //为什么直接除以10就可以了?为什么任意进制转换 不可随意丢掉最后一位?t[0]/=m 没有丢掉最后一位啊 //淦,你果然写错了,所以你的质疑是对的
}
reverse(ans.begin(),ans.end());
return ans;
}
ll toTen(string s,int k){
ll base=1,ans=0;
int len=s.size();
for(int i=len-1;i>=0;--i){
if(s[i]<='9') ans+=(s[i]-'0')*base;
else ans+=(s[i]-'A'+10)*base;
base*=k;
}
return ans;
}
int main(){
int T;
scanf("%d",&T);
bool flag=0;
int k=10;
string op,opp;
string a;
ll ans=0;
ll num[2]={0,0};
while(T--){
cin>>op;
if(op=="CLEAR"){
flag=0;
ans=0;
num[0]=num[1]=0;
}else if(op=="NUM"){
cin>>a;
//cout<<"a:"<<a<<endl;
num[flag]=toTen(a,k);
//cout<<"1num:"<<num[0]<<" "<<num[1]<<"\n";
if(flag){
//cout<<"2num:"<<num[0]<<" "<<num[1]<<"\n";
if(opp=="ADD") {ans=num[0]+num[1];}
if(opp=="SUB") {ans=num[0]-num[1];}
if(opp=="MUL") {ans=num[0]*num[1];}
if(opp=="DIV") {ans=num[0]/num[1];}
if(opp=="MOD") {ans=num[0]%num[1];}
num[0]=ans;num[1]=0;
flag=0;
}else ans=num[0];
}else if(op=="CHANGE"){
scanf("%d",&k);
}else if(op=="EQUAL"){
cout<<toAns(ans,k)<<endl;
}else{
opp=op;
flag=1;
}
}
}