前几天看到某小学毕业模拟考试有一道编程题,编写一个简单的计算器程序,要求支持小数和负数运算,不能调用math库,还不能使用eval等表达式求值函数,这还不算完,居然还要求要能够提示输入错误,对于小学生来讲,这样的题目确实还是蛮麻烦的,所以有小学生找到我,让我帮帮忙,我没办法,只能尝试着写一写。
我写的这个程序虽然不是很完美,但是也算是符合要求了。完全没有调用math库,实现了常用的数学函数,如sin,log,pow等,而且还实现了和python中eval函数类似的功能,同时还支持括号匹配检测,包括括号的优先级(即小括号在内,中括号在外),而且对一些常见的错误都可以给出提示。
有需要的同学可以拿去参考参考,里面的括号匹配和表达式求值的过程还是很值得一看的。
下面给一个连接,里面包含了源程序、使用说明书和讲解视频,大家可以下载,我的建议是,大家在使用前一定先看一下使用说明书!一定先看一下使用说明书!一定先看一下使用说明书!
链接:https://pan.baidu.com/s/1vLbVC8seXCpWjcJNXEVFLA
提取码:e2jd
下面展示一下效果吧!
程序如下:
# -*- coding: utf-8 -*-
"""
Created on Fri May 6 01:14:57 2022
@author: 2540817538
环境:Windows 10 Spyder 4 Python 3.8
使用前请先查看使用说明书!!!!
"""
import re#导入re,用于正则表达式匹配
from tkinter import *#导入thinter用于用户图形界面制作
import tkinter.messagebox
###############################################################################
#创建栈类,后面的括号匹配和表达式求值会用到栈,不过也不一定非要用栈,直接进行字符串的处理也是可以的
class myStack(object):
def __init__(self):# 初始化栈为空列表
self.items = []
def isEmpty(self):# 判断栈是否为空
return self.items == []
def peek(self): # 返回栈顶元素
return self.items[len(self.items) - 1]
def size(self): # 返回栈的大小
return len(self.items)
def push(self, item): # 进栈
self.items.append(item)
def pop(self): # 出栈
return self.items.pop()
def comlist(self):#返回整个栈
return self.items
###############################################################################
####多种函数的实现,该部分相当于实现math库的部分功能
def sin(x):#正弦函数,利用的泰勒展开式,这里值列出了sin cos 和tan,arcsin等也是利用泰勒展开式,原理类似,
x=x*pi()/180#因此就不单独去写arcsin,arccos,arctan等函数了,注意x应该是角度而非弧度
s=1
sinx=0
a=x#a作为分子
b=1#b作为分母
i=1
while(abs(a/b)>=1e-15):
sinx=sinx+s*a/b#累加一项
a=a*x*x#求下一项分子
b=b*2*i*(2*i+1)
s=s*(-1)
i=i+1
return round(sinx,6)#这里的精度会影响到后面cos和tan的计算,所以最好多保留几位有效数字
def cos(x) :#余弦函数
return sin(90-x)
def tan(x):#正切函数
if (x+90)%180!=0:#其实这里不必单独考虑x的取值范围,因为如果x为负数,后面的表达式检测函数会进行报警
tanx=sin(x)/cos(x)
return round(tanx,6)
def rootsqu(x):#开平方函数,这里不必单独考虑x的取值范围,因为如果x为负数,后面的表达式检测函数会进行报警
root=x
while root*root>x:
root=(root+x/root)/2
return root
def pows(x,n):#指数函数,这里利用了分治策略,可以降低时间复杂度
if n<0:
n=-n
result=1/pows(x,n)
else:
if n==0:
result=1
else:
if n%2==0:
result=pows(x*x,n/2)
else:
result=pows(x*x,(n-1)/2)*x
return result
def multi(x,n):#n个x相乘
result=1
if n==0:
return 1
for i in range(n):
result =result*x
return result
def ln(x):#对数函数,如果要求log可以利用公式ln(a)/ln(b)求得
ln10=2.302585
k=0
while x>1:
x=x/10
k=k+1
y=x-1
result=ln10*k
s=i=1
while i <100:
result =s*multi(y,i)/i+result
s=(-1)*s
i=i+1
return round(result,4)
def percent(x):#求百分数
return x/100
def e():#e值计算,还是泰勒展开
result=1
cur=1
i=1
while i<=20:#迭代次数可以根据精度需求自行设置,一般设置在15次以上
cur=cur *i
result=result+1/cur
i=i+1
return result
def pi():#圆周率值
result=0
for i in range(20):#迭代次数可以根据精度需求自行设置,一般设置在15次以上
result =result+1/pows(16,i)*(4/(8*i+1)-2/(8*i+4)-1/(8*i+5)-1/(8*i+6))
return result
def sigmoid(x):#sigmiod函数实现
return round(1.0/(1 + pows(e(),-x)),4)
def rootcub(x):#求取立方根,这里利用了牛顿迭代法
result=x/2
while abs(result*result*result-x)>1e-5:
result=result-(result*result*result-x)/(3*result*result)
return round(result ,4)
def log(x,y):#对数函数
return round(ln(y)/ln(x),4)
##############################################################################
####下面是表达式求值的核心模块,包括三个核心函数,其功能与内置的eval函数大同小异
def compute (num1,num2,operator):#遍历到操作符时压栈方法
result =0
if operator=="+":
result=num1+num2
if operator=="-":
result=num2-num1#接近栈底的是被减数
if operator=="*":
result=num1*num2
if operator=="/":
if num1!=0:
result=num2/num1#接近栈底的是被除数
return result
def priority(str1):#定义运算符优先级
n=0
if str1=="+" or str1=="-":
n=-1
if str1=="*" or str1=="/":
n=1
if str1=="(":
n=-2
if str1==")":
n=2
return n
def calculate(string):#计算后缀表达式并得到结果
expression=[]
expression=string.split(" ")#用空格分割字符串
stack1=myStack()#实例化三个栈,一个存放后缀表达式,一个存放运算符,一个用于运算
stack2=myStack()
stack3=myStack()
try:
for i in range(len(expression)):
if regulmatch(expression[i]):#正则表达式匹配浮点数
stack1.push(expression[i])
elif stack2.isEmpty(): #括号以及加减乘除的入栈操作
stack2.push(expression[i])
elif expression[i]=="(":
stack2.push(expression[i])
elif expression[i]==")":
while not(stack2.peek()=="("):
stack1.push(stack2.pop())
stack2.pop()
elif expression[i] in '+-*/(' :#加减乘除入栈
while not(stack2.isEmpty()) and (priority(expression[i])<=priority(stack2.peek())):
stack1.push(stack2.pop())
stack2.push(expression[i])
else :#小数点直接入栈
stack1.push(expression[i])
while not(stack2.isEmpty()):#当运算符栈不为空时,将运算符全部弹入 stack1
stack1.push(stack2.pop())
for j in range(stack1.size()):#遍历后缀表达式
element=stack1.comlist()[j]
if regulmatch(element):#正则表达式匹配数字
stack3.push(element)
else:
if stack3.isEmpty():
num1="0"
else:
num1=stack3.pop()
if stack3.isEmpty():
num2="0"
else:
num2=stack3.pop()
result =compute(float(num1),float(num2),element)#计算
stack3.push(str(result))
return round(float(stack3.pop()),4)#为了方便,最后的结果就保留四位小数了
except:
tkinter.messagebox.showerror("表达式错误","表达式存在一些问题,例如数字直接连接函数或e、π,请仔细检查后重新输入")
return string
###############################################################################
#正则表达式匹配数字
def regulmatch(ch):
return re.match( "-?\\d+\\.*\\d*",ch)
#cal_raplace函数用来对对输入的表达式进行一些预处理,主要是将函数的值先求出来,让表达式不在含有各个函数,而是将其替换成函数的计算结果
#请注意,函数会优先选择匹配数字,比如输入- 2 pows 4,程序默认为输入的是-( 2 pows 4 )
#并且程序不支持链接括号,比如sin(30 + 30)是非法的,应该直接写成sin 60
def cal_replace(string):
string=string.replace(' ',' ')
expression=string.split(" ")#用空格分割字符串
flag=0#这个标志用来记录表达式中是否有替换的地方,用以解决函数嵌套问题,例如ln ln 5的情况
set1={'sin','cos','tan','rootcub','rootsqu','pows','sigmoid'}
try:
for i in range(len(expression)):
if expression[i]=='(' and expression[i+1]=='-':#这里的处理是为了方便复数的运算,例如1-(-2)
string=string.replace('( - ','( -')
flag=1
if expression[i]=="e":#以下内容基本上都是求函数值,比如将表达式中的sin30替换成0.5
result=e()
string=string.replace('e', str(result))
flag=1
if expression[i]=="π":
result=pi()
string=string.replace('π', str(result))
flag=1
if expression[i] in set1 and expression[i+1] in '-' and regulmatch(expression[i+2]):
string=string.replace(expression[i+1]+' '+expression[i+2], str(float(expression[i+2])*(-1)))
flag=1
if expression[i]=="pows" and regulmatch(expression[i+1]) and regulmatch(expression[i-1]) and float(expression[i+1]).is_integer():
result=pows(float(expression[i-1]),float(expression[i+1]))
string=string.replace(expression[i-1]+' pows '+expression[i+1], str(result))
flag=1
if expression[i]=="log" and regulmatch(expression[i+1]) and regulmatch(expression[i-1]) and float(expression[i-1])>0 and float(expression[i+1])>0:
result=log(float(expression[i-1]),float(expression[i+1]))
string=string.replace(expression[i-1]+' log '+expression[i+1], str(result))
flag=1
if expression[i]=="sin"and regulmatch(expression[i+1]):
result=sin(float(expression[i+1]))
string=string.replace('sin '+expression[i+1], str(result))
flag=1
if expression[i]=="cos" and regulmatch(expression[i+1]):
result=cos(float(expression[i+1]))
string=string.replace('cos '+expression[i+1], str(result))
flag=1
if expression[i]=="tan" and regulmatch(expression[i+1]) and (float(expression[i+1])+90)%180!=0:
result=tan(float(expression[i+1]))
string=string.replace('tan '+expression[i+1], str(result))
flag=1
if expression[i]=="rootsqu" and regulmatch(expression[i+1]) and float(expression[i+1])>=0:
result=rootsqu(float(expression[i+1]))
string=string.replace('rootsqu '+expression[i+1], str(result))
flag=1
if expression[i]=="rootcub" and regulmatch(expression[i+1]):
result=rootcub(float(expression[i+1]))
string=string.replace('rootcub '+expression[i+1], str(result))
flag=1
if expression[i]=="ln" and regulmatch(expression[i+1]) and float(expression[i+1])>0:
result=ln(float(expression[i+1]))
string=string.replace('ln '+expression[i+1], str(result))
flag=1
if expression[i]=="%" and regulmatch(expression[i-1]) :
result=percent(float(expression[i-1]))
string=string.replace(expression[i-1]+" %", str(result))
flag=1
if expression[i]=="sigmoid" and regulmatch(expression[i+1]) and float(expression[i+1]).is_integer():
result=sigmoid(float(expression[i+1]))#因为用到了pows函数,pows不支持指数为小数
string=string.replace('sigmoid '+expression[i+1], str(result))
flag=1
if flag==1:#如果表达式中出现替换,那么就需要递归调用该函数,解决例如sin sin 30的问题
string=cal_replace(string)
return string
except :#并不能保证表达式能够正常替换,比如输入tan tan tan,最后没有数字,这种情况显然不合理,因此需要抛出异常
tkinter.messagebox.showerror("表达式错误",'表达式存在一些问题,请仔细检查后输入正确的表达式')
return string
###############################################################################
#将表达式中的括号提取出来方便处理,不过不提出来影响也不大
def find_bra(string):
result=''
for i in string:
if i in "[]()":
result=result+i
return result
#match函数是用于括号匹配的函数,因为这里的[]()存在优先级的关系,所以直接用栈来完成会很复杂,比较方便的一种方式是
#用栈配合和字符串的检测来完成
def match(string):
string=find_bra(string)
bracket=[]
try:
for i in range(len(string)):
if string[i] in "[](){}" :#由于{}判断原理与()[]相同,且本计算器中没有{},所以后面的部分讨论就没有再考虑{}
bracket.append(string[i])
if len(bracket)%2!=0:#括号数为奇数的直接进行报错
ans=string
if "()" in string:
ans=ans.replace("()", "")
if "[]" in string:
ans=ans.replace("[]", "")
tkinter.messagebox.showerror("括号匹配错误",'对不起,语法错误,'+ans+'使用不合理')
return False
if "[]" in string:#这一部分可以检测出括号优先级出错的情况,这里不需要考虑{}的情况
tkinter.messagebox.showerror("括号匹配错误","对不起,语法错误,[ ]使用不合理,使用( )后才能使用[ ]")
return False
if "((" in string:
tkinter.messagebox.showerror("括号匹配错误","对不起,语法错误,( )使用不合理,内层使用( )后外层应使用[ ]")
return False
if "[[" in string:
tkinter.messagebox.showerror("括号匹配错误","对不起,语法错误,[ ]使用不合理,内层使用[ ]后外层应使用{ }")
return False
if "([" in string:
tkinter.messagebox.showerror("括号匹配错误","对不起,语法错误,([ ])使用不合理,( )应放在[ ]内层")
return False
braStack = myStack()#创建类实例
leftbkt = "{[("
rightbkt = "}])"
for i in string:#这一部分用于检测左括号和右括号不匹配的情况
if i in leftbkt:
braStack.push(i)
elif i in rightbkt:
if braStack.isEmpty():
tkinter.messagebox.showerror("括号匹配错误","对不起,语法错误, "+i+" 使用不合理")
return False
if rightbkt.index(i) != leftbkt.index(braStack.pop()):
if '[)' in string:
i='['
tkinter.messagebox.showerror("括号匹配错误","对不起,语法错误, "+i+" 使用不合理")
return False
if braStack.isEmpty():
return True
else:
tkinter.messagebox.showerror("括号匹配错误","对不起,语法错误, "+braStack.pop()+" 使用不合理")
return False
except:
tkinter.messagebox.showerror("括号匹配错误","在括号匹配过程中遇到一些错误,请重新输入表达式")
return False
###############################################################################
#这个函数输出字符串中小数点数目主要是用来检测小数点是否错误,比如出现1.2.3这种错误的格式
def count_char(str):
dict = 0
for i in str:
if i =='.':
dict += 1
return dict
#char_judge函数主要是用来解决e和π连续输入,跟数字和函数时出错的情况,例如etan、e9等情况
def char_judge(string):
setwrong={'πe','eπ','ππ','ee','πt','πs','πc','πl','et','es','ec','el','πr','er'}
setwrong2={'π0','π1','π2','π3','π4','π5','π6','π7','π8','π9','e1','e0','e2','e3','e4','e5','e6','e7','e8','e9'}
for i in setwrong :
if i in string:
return True
for i in setwrong2 :
if i in string:
return True
return False
#find_wrong函数是用来检测表达式合法性的主要函数,主要检测一些比较容易描述的典型错误,主要包括复数的输入格式错误、eπ的使用问题,
#运算符、小数点的问题、函数的输入格式和取值范围问题等,一些不便于描述的错误直接统一报错
def find_wrong(string):
string1=string.replace(" ", "")#一部分检测需要先将表达式中的空格去掉才能进行
set1='*%/.'
set3='+-*/'
set2='0123456789'
set4={"sin","cos",'tan',"ln","sigmoid","rootsqu","rootcub",'log','pows'}
set5={'log','pows'}
try:#前一部分检测的是去掉空格后的字符串
if "+-" in string1 or "/-" in string1 or "--" in string1 or "*-" in string1:#表达式中间的复数最好写成(-x)的形式
tkinter.messagebox.showerror('表达式输入错误',"请将复数写成0-x的形式,或者写成(-x)")
return False
if string1[0] in set1:#这些符号出现在表达式最前面显然是错误的
tkinter.messagebox.showerror('表达式输入错误',"表达式的第一个符号使用不合理,请仔细检查后正确输入")
return False
if string1[-1] in set3:
tkinter.messagebox.showerror('表达式输入错误',"表达式的最后一个符号使用不合理,请仔细检查后正确输入")
return False
if char_judge(string1) :
tkinter.messagebox.showerror('表达式输入错误',"e或π的使用有问题,请仔细检查后正确输入")
return False
for i in range(len(string1)):#这里的i不用考虑越界问题,因为越界后后面会抛出异常
if string1[i]=='.' and i!=0 and i!=len(string1)-1:#小数点必然在两个数字之间
if (string1[i-1] not in set2) or (string1[i+1] not in set2):
tkinter.messagebox.showerror('表达式输入错误',".的使用不正确,请仔细检查后正确输入")
return False
if string1[i]=='/' and i!=0 and i!=len(string1)-1:#加减乘除的判断,检测是否有连续输入运算符的情况,例如2++1,3*-1
if (string1[i-1] in '+-*/') or (string1[i+1] in '+-*/%'):
tkinter.messagebox.showerror('表达式输入错误',"/的使用不正确,请仔细检查后正确输入")
return False
if string1[i]=='+' and i!=0 and i!=len(string1)-1:
if (string1[i-1] in '+-*/') or (string1[i+1] in '+-*/%'):
tkinter.messagebox.showerror('表达式输入错误',"+的使用不正确,请仔细检查后正确输入")
return False
if string1[i]=='-' and i!=0 and i!=len(string1)-1:
if (string1[i-1] in '+-*/') or (string1[i+1] in '+-*/%'):
tkinter.messagebox.showerror('表达式输入错误',"-的使用不正确,请仔细检查后正确输入")
return False
if string1[i]=='*' and i!=0 and i!=len(string1)-1:
if (string1[i-1] in '+-*/') or (string1[i+1] in '+-*/%'):
tkinter.messagebox.showerror('表达式输入错误',"*的使用不正确,请仔细检查后正确输入")
return False
if string1[i]=='%' and (string1[i+1] not in '+-*/)]' or string[i-1] in set4 ):
tkinter.messagebox.showerror('表达式输入错误','%的使用不正确,请仔细检查后正确输入')
return False
if string1[i]=='/' and string1[i+1]=='0':#除数不能为0的检测
tkinter.messagebox.showerror('表达式错误',"语法错误,除数不能为0,请仔细检查后正确输入")
return False
expression=[]#以下部分需要将字符串通过空格进行分割后再检测
string1=string.replace(" ", " ")
expression=string.split(" ")#用空格分割字符串
if expression[-1] in set4:
tkinter.messagebox.showerror('表达式输入错误',"数学函数的使用存在问题,请仔细检查后正确输入")
return False
if expression[0] in set5:
tkinter.messagebox.showerror('表达式输入错误',"数学函数的使用存在问题,请仔细检查后正确输入")
return False
for i in expression:
if count_char(i)>1:
tkinter.messagebox.showerror('表达式输入错误',"表达式中存在不正确的数字:"+i+',请仔细检查后正确输入')
return False
for i in range(len(expression)-1):#这里主要检测的是取值范围和函数的格式问题,例如sin(30+30)是不正确的,应该写为sin60
if expression[i] in set4 and expression[i+1] =='(':
tkinter.messagebox.showerror('表达式输入错误','该数学函数不支持嵌套表达式,请将括号内的式子单独计算,再使用该函数')
return False
if (expression[i]=='log' or expression[i]=='pows' ) and expression[i-1]==')':
tkinter.messagebox.showerror('表达式输入错误','该数学函数不支持嵌套表达式,请将括号内的式子单独计算,再使用该函数')
return False
if (expression[i]=='log' or expression[i]=='pows' ) and (expression[i-1]=='' or expression[i-1] in "+-*/%."):
tkinter.messagebox.showerror('表达式输入错误','函数缺少一个输入值,请仔细检查后正确输入')
return False
if (expression[i]=='log' or expression[i]=='pows' ) and (expression[i+1]=='' or expression[i+1] in "+-*/%."):
tkinter.messagebox.showerror('表达式输入错误','函数缺少一个输入值,请仔细检查后正确输入')
return False
if expression[i]=='tan' and (float(expression[i+1])+90)%180==0:
tkinter.messagebox.showerror('表达式输入错误','tan取值有问题,请仔细检查后正确输入')
return False
if expression[i]=='ln'and expression[i+1]=='-':
tkinter.messagebox.showerror('表达式输入错误','ln取值有问题,请仔细检查后正确输入')
return False
if expression[i]=='log'and (expression[i+1]=='-' or expression[i+1]=='0'):
tkinter.messagebox.showerror('表达式输入错误','log取值有问题,请仔细检查后正确输入')
return False
if expression[i]=='ln'and (expression[i+1]=='0' or float(expression[i+1])<0):
tkinter.messagebox.showerror('表达式输入错误','ln取值有问题,请仔细检查后正确输入')
return False
if expression[i]=='log'and (float(expression[i-1])<=0 or float(expression[i+1])<=0):
tkinter.messagebox.showerror('表达式输入错误','log取值有问题,请仔细检查后正确输入')
return False
if expression[i]=='rootsqu'and float(expression[i+1])<0 :
tkinter.messagebox.showerror('表达式输入错误','rootsqu取值有问题,请仔细检查后正确输入')
return False
if (expression[i]=='sigmoid' or expression[i]=='pows' ) and not(float(expression[i+1]).is_integer()):
tkinter.messagebox.showerror('表达式输入错误','该数学函数不支持小数,请仔细检查后正确输入')
return False
return True
except:#这里主要是考虑到异常输入会使前面的检测出现越界的情况,比如tan%等,还有一些不便于描述的错误,在这里一起抛出
tkinter.messagebox.showerror('表达式输入错误','表达式输入存在错误,请仔细检查后正确输入')
return False
###############################################################################
#######下面主要是和GUI生成的模块
#这个函数将[]转换成(),在进行括号匹配检测后,[]已经没有意义,正常的计算器只需要()就足够了,calculate函数也不需要单独用[]
def transbra(string):
string=string.replace('[','(')
string=string.replace(']',')')
return string
def button_click(string):#数字和函数按钮的相应
global calc_operator#calc_operator必须设置成全局变量,因为在多个函数中都将对其进行操作
calc_operator=calc_operator+string
calc_operator1=calc_operator.replace(' ',"")#将表达式中大量的空格去掉后再显示
text_input.set(calc_operator1)
def button_clear_all():#AC按钮的响应
global calc_operator
calc_operator=""
text_input.set("")
def button_delete():#⌫按钮的响应
global calc_operator
text=calc_operator[:-1]
calc_operator=text
text_input.set(text)
def button_equal():#=按钮的响应
global calc_operator
string=calc_operator
string=string.replace(' ',' ')#部分情况下表达式中会出现连续两个空格,这时候需要去掉一个空格,以免影响后续使用
a=match(string)
string=cal_replace(string)
b=find_wrong(string)#这里可以改成a为True的时候才执行,就可以减少执行量,提高速度
if a and b:
string=transbra(string)#[]转化为()
print('计算的表达式为:',calc_operator.replace(' ',''))
temp_op=str(calculate(string))
text_input.set(temp_op)
calc_operator=temp_op
else:
print('计算的表达式为:',string.replace(' ',''))
calc_operator=""
tk_calculate=Tk()
tk_calculate.configure(bg="#d3d7d4", bd=10)
tk_calculate.title("网宿科技")
calc_operator=""
text_input=StringVar()
#文本框
text_display=Entry(tk_calculate, font=('sans-serif', 27, 'bold'), textvariable=text_input,
bd=5, insertwidth = 5, bg='#fffffb', justify='right').grid(columnspan=5, padx = 10, pady = 15)
button_params={'bd':5, 'fg':'#BBB', 'bg':'#3C3636', 'font':('sans-serif', 20, 'bold')}#按钮格式的统一设置
button_params_main={'bd':5, 'fg':'#000', 'bg':'#BBB', 'font':('sans-serif', 20, 'bold')}
#下面是各个按钮的排列,格式基本上都一样
#第一行
button_sin=Button(tk_calculate, button_params, text='sin',
command=lambda:button_click('sin ')).grid(row=1, column=0, sticky="nsew")
button_cos=Button(tk_calculate, button_params, text='cos',
command=lambda:button_click('cos ')).grid(row=1, column=1, sticky="nsew")
button_tan=Button(tk_calculate, button_params, text='tan',
command=lambda:button_click('tan ')).grid(row=1, column=2, sticky="nsew")
button_e=Button(tk_calculate, button_params, text=' e ',
command=lambda:button_click('e')).grid(row=1, column=3, sticky="nsew")
button_pi=Button(tk_calculate, button_params, text=' π ',
command=lambda:button_click('π')).grid(row=1, column=4, sticky="nsew")
#第二行
button_root2=Button(tk_calculate, button_params, text='\u00B2\u221A',
command=lambda:button_click('rootsqu ')).grid(row=2, column=0, sticky="nsew")
button_root3=Button(tk_calculate, button_params, text='\u00B3\u221A',
command=lambda:button_click('rootcub ')).grid(row=2, column=1, sticky="nsew")
button_pows=Button(tk_calculate, button_params, text='x^n',
command=lambda:button_click(' pows ')).grid(row=2, column=2, sticky="nsew")
button_sigmoid=Button(tk_calculate, button_params, text='sigmoid',font=("宋体",10),
command=lambda:button_click('sigmoid ')).grid(row=2, column=3, sticky="nsew")
button_log=Button(tk_calculate, button_params, text='log ',
command=lambda:button_click(' log ')).grid(row=2, column=4, sticky="nsew")
#第三行
button_kuol1=Button(tk_calculate, button_params, text='(',
command=lambda:button_click('( ')).grid(row=3, column=0, sticky="nsew")
button_kuor1=Button(tk_calculate, button_params, text=')',
command=lambda:button_click(' )')).grid(row=3, column=1, sticky="nsew")
button_kuol2=Button(tk_calculate, button_params, text='[',
command=lambda:button_click('[ ')).grid(row=3, column=2, sticky="nsew")
button_kuor2=Button(tk_calculate, button_params, text=']',
command=lambda:button_click(' ]')).grid(row=3, column=3, sticky="nsew")
button_ln=Button(tk_calculate, button_params, text='ln', font=('sans-serif', 15, 'bold'),
command=lambda:button_click('ln ')).grid(row=3, column=4, sticky="nsew")
#第四行
button_0=Button(tk_calculate, button_params_main, text='0',
command=lambda:button_click('0')).grid(row=4, column=0, sticky="nsew")
button_point=Button(tk_calculate, button_params_main, text='.',
command=lambda:button_click('.')).grid(row=4, column=1, sticky="nsew")
button_percent=Button(tk_calculate, button_params_main, text='%',
command=lambda:button_click(' %')).grid(row=4, column=2, sticky="nsew")
button_delete_one=Button(tk_calculate, bd=5, fg='#000', font=('sans-serif', 20, 'bold'),
text='⌫', command=button_delete, bg='#db701f').grid(row=4, column=3, sticky="nsew")
button_delete_all=Button(tk_calculate, bd=5, fg='#000', font=('sans-serif', 20, 'bold'),
text='AC', command=button_clear_all, bg='#db701f').grid(row=4, column=4, sticky="nsew")
#第五行
button_7=Button(tk_calculate, button_params_main, text='7',
command=lambda:button_click('7')).grid(row=5, column=0, sticky="nsew")
button_8=Button(tk_calculate, button_params_main, text='8',
command=lambda:button_click('8')).grid(row=5, column=1, sticky="nsew")
button_9=Button(tk_calculate, button_params_main, text='9',
command=lambda:button_click('9')).grid(row=5, column=2, sticky="nsew")
button_mul=Button(tk_calculate, button_params_main, text='*',
command=lambda:button_click(' * ')).grid(row=5, column=3, sticky="nsew")
button_dev=Button(tk_calculate, button_params_main, text='/',
command=lambda:button_click(' / ')).grid(row=5, column=4, sticky="nsew")
#第六行
button_4=Button(tk_calculate, button_params_main, text='4',
command=lambda:button_click('4')).grid(row=6, column=0, sticky="nsew")
button_5=Button(tk_calculate, button_params_main, text='5',
command=lambda:button_click('5')).grid(row=6, column=1, sticky="nsew")
button_6=Button(tk_calculate, button_params_main, text='6',
command=lambda:button_click('6')).grid(row=6, column=2, sticky="nsew")
button_add=Button(tk_calculate, button_params_main, text='+',
command=lambda:button_click(' + ')).grid(row=6, column=3, sticky="nsew")
button_sub=Button(tk_calculate, button_params_main, text='-',
command=lambda:button_click(' - ')).grid(row=6, column=4, sticky="nsew")
#第七行
button_1=Button(tk_calculate, button_params_main, text='1',
command=lambda:button_click('1')).grid(row=7, column=0, sticky="nsew")
button_2=Button(tk_calculate, button_params_main, text='2',
command=lambda:button_click('2')).grid(row=7, column=1, sticky="nsew")
button_3=Button(tk_calculate, button_params_main, text='3', font=('sans-serif', 16, 'bold'),
command=lambda:button_click('3')).grid(row=7, column=2, sticky="nsew")
button_equal=Button(tk_calculate, button_params_main, text='=',
command=button_equal).grid(row=7, columnspan=2, column=3, sticky="nsew")
tk_calculate.mainloop()
#转载请注明作者