python练习---模拟计算器

时间:2022-09-25 06:19:45
#!/bin/env python
# -*- coding:utf-8 -*-
'''
实现能计算类似
1 - 2 * ( (60-30 +(-40/5) * (9-2*5/3 + 7 /3*99/4*2998 +10 * 568/14 )) - (-4*3)/ (16-3*2))公式
'''

import re

def cal_mini_exp(mini):
    #计算40/5 2*5这样的表达式
    if '*' in mini:
        mun1,mun2 = mini.split('*')
        return str(float(mun1) * float(mun2))
    elif '/' in mini:
        mun1, mun2 = mini.split('/')
        return str(float(mun1) / float(mun2))



def conform(exp):
    exp = exp.replace('--','+')
    exp = exp.replace('+-','-')
    exp = exp.replace('-+','-')
    exp = exp.replace('++','+')
    return exp

def calculate(son_exp):
    '''
    计算内部不在有小括号表达式的结果
    :param exp:
    :return:
    '''
    son_exp = son_exp.strip('()')
    while True:   #完成一个表达式乘除法的计算
        ret = re.search('\d+\.?\d*[*/]-?\d+\.?\d*',son_exp)      #9-2*5/3+7/3*99/4*2998+10*568/14 匹配乘除表达式
        if ret:
            mini_exp = ret.group()
            # 40/5 2*5
            res = cal_mini_exp(mini_exp)  #40/5=8
            son_exp = son_exp.replace(mini_exp,res,1)
        else:break

    son_exp = conform(son_exp)   #整理表达式中的符号
    ret_l = re.findall('[+-]?\d+\.?\d*',son_exp)
    sum = 0
    for i in ret_l:
        sum += float(i)

    return str(sum)



exp = '1 - 2 * ( (60-30 +(-40/5) * (9-2*5/3 + 7 /3*99/4*2998 +10 * 568/14 )) - (-4*3)/ (16-3*2))'
a = exp
#去空格
exp = exp.replace(' ','')
#print(exp)

while True:
    #把表达中所有的小括号表达式都计算出来
    ret = re.search('\([^()]+\)',exp)   #是否匹配上的对象
    if ret:
        son_exp = ret.group()    #子表达式
        print('匹配小括号:%s' % son_exp)
        #计算乘除法,再计算加减
        ret = calculate(son_exp)

        exp = exp.replace(son_exp,ret,1)
    else:
        break


print('最外层括号表达式:%s' % exp)
ret = calculate(exp)
print(ret)
print('eval结果:',eval(a))