Python技巧----函数作为参数以及dict代替if

这是tkinter的代码,command参数表示按钮对应的动作,这个参数是个函数

# 操作符按钮
self.btn_add = tk.Button(self.tkwindow, text='+', command=self.command_add)
self.btn_add.pack(padx=1, side='left')

self.btn_minus = tk.Button(self.tkwindow, text='-', command=self.command_minus)
self.btn_minus.pack(padx=1, side='left')
        
self.btn_multiply = tk.Button(self.tkwindow, text='*', command=self.command_multipy)
self.btn_multiply.pack(padx=1, side='left')

self.btn_divide = tk.Button(self.tkwindow, text='/', command=self.command_divide)
self.btn_divide.pack(padx=1, side='left')

'''
省略
'''

    def command_add(self):
        if self.op_can_use:
            self.op_now = '+'
            self.op_pressed = True

    def command_minus(self):
        if self.op_can_use:
            self.op_now = '-'
            self.op_pressed = True

    def command_multipy(self):
        if self.op_can_use:
            self.op_now = '*'
            self.op_pressed = True

    def command_divide(self):
        if self.op_can_use:
            self.op_now = '/'
            self.op_pressed = True

 

但这4个command的函数几乎长得一模一样啊,有四个还好,如果有十几个怎么办,能不能精简点

    def command_op(self, op):
        if self.op_can_use:
            self.op_now = op
            self.op_pressed = True

    def command_add(self):
        return self.command_op('+')
    def command_minus(self):
        return self.command_op('-')
    def command_multipy(self):
        return self.command_op('*')
    def command_divide(self):
        return self.command_op('/')    

 

 

和dict配合使用

self.opdict = {'+': add, '-': minus, '*': multiply, '/': divide}


#这是调用,根据op_now选择对应的函数,代替if判断
self.opnum = self.opdict[self.op_now](self.opnum, self.num_temp)[0]

 

 

 

全部代码,计算24点,用tkinter做了界面,两个文件一个界面,一个计算24点的函数

# enconding:utf-8
# file point24/gui

import tkinter as tk
import random
from point24.bk import cal_24point, add, minus, multiply, divide

class Window:
    def __init__(self, title='24点', width=650, height=400):

        self.w = width
        self.h = height
        self.tkwindow = tk.Tk(className=title)
        self.opdict = {'+': add, '-': minus, '*': multiply, '/': divide}
        self.init_status()
        self.add_compnent()

    def init_status(self):


        self.op_pressed = False
        self.op_now = ''
        self.opnum = 0
        self.num_temp = 0
        self.num_count = 0
        self.op_can_use = False
        self.btn_num_temp_used = False

    def fournumber(self):
        TEN_OR_K = 10
        self.num1 = random.randint(1, TEN_OR_K)
        self.num2 = random.randint(1, TEN_OR_K)
        self.num3 = random.randint(1, TEN_OR_K)
        self.num4 = random.randint(1, TEN_OR_K)

    def add_compnent(self):
        B_WIDTH = 6
        B_HEIGHT = 5

        self.label_ans = tk.Label(text="answer", fg="black", bg="white")
        self.label_ans.pack()

        # 数字按钮
        self.fournumber()
        self.btn_num1 = tk.Button(self.tkwindow, text=self.num1, 
                                  command=self.command_num1,
                                  width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_num1.pack(side='left')

        self.btn_num2 = tk.Button(self.tkwindow, text=self.num2,
                                  command=self.command_num2,
                                  width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_num2.pack(side='left')

        self.btn_num3 = tk.Button(self.tkwindow, text=self.num3,
                                  command=self.command_num3,
                                  width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_num3.pack(side='left')
        
        self.btn_num4 = tk.Button(self.tkwindow, text=self.num4, 
                                  command=self.command_num4,
                                  width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_num4.pack(side='left')

        self.btn_num_temp = tk.Button(self.tkwindow, text=self.num_temp, 
                                      command=self.command_num_temp,
                                  width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_num_temp.pack(side='bottom')

        # 操作符按钮
        self.btn_add = tk.Button(self.tkwindow, text='+', 
                                 command=self.command_add,
                                 width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_add.pack(padx=1, side='left')

        self.btn_minus = tk.Button(self.tkwindow, text='-', 
                                   command=self.command_minus,
                                   width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_minus.pack(padx=1, side='left')
        
        self.btn_multiply = tk.Button(self.tkwindow, text='*', 
                                      command=self.command_multipy,
                                      width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_multiply.pack(padx=1, side='left')

        self.btn_divide = tk.Button(self.tkwindow, text='/', 
                                    command=self.command_divide,
                                    width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_divide.pack(padx=1, side='left')

        # 功能按钮
        self.btn_change = tk.Button(self.tkwindow, text='换一组', 
                                    command=self.command_change,
                                    width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_change.pack(padx=1, side='right')

        self.btn_answer = tk.Button(self.tkwindow, text='显示答案', 
                                    command=self.command_answer,
                                 width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_answer.pack(padx=1, side='right')

        self.btn_clear = tk.Button(self.tkwindow, text='清除', 
                                   command=self.command_clear,
                                 width=B_WIDTH, height=B_HEIGHT,relief='groove')
        self.btn_clear.pack(padx=1, side='right')

    # 一个数字只能按一次,按错了用clear重来
    def command_clear(self):
        self.btn_num1['state'] = 'active'
        self.btn_num2['state'] = 'active'
        self.btn_num3['state'] = 'active'
        self.btn_num4['state'] = 'active'
        self.btn_num_temp['state'] = 'active'
        self.btn_num_temp['text'] = '0'
        self.label_ans['text'] = 'answer'
        self.init_status()

    def command_answer(self):
        ans = cal_24point(self.num1, self.num2, self.num3, self.num4)
        self.label_ans['text'] = str(ans)

    def command_change(self):
        self.fournumber()
        self.btn_num1['text'] = self.num1
        self.btn_num2['text'] = self.num2
        self.btn_num3['text'] = self.num3
        self.btn_num4['text'] = self.num4
        self.command_clear()

    def command_op(self, op):
        if self.op_can_use:
            self.op_now = op
            self.op_pressed = True

    def command_add(self):
        return self.command_op('+')

    def command_minus(self):
        return self.command_op('-')

    def command_multipy(self):
        return self.command_op('*')

    def command_divide(self):
        return self.command_op('/')    

    def command_num_temp(self):
        if self.op_pressed:
            self.opnum = self.opdict[self.op_now](self.opnum, self.num_temp)[0]
            self.btn_num_temp['text'] = self.opnum
            self.num_temp = self.opnum
        else:
            self.opnum = self.num_temp
        print(self.opnum)
        self.op_pressed = False
        self.btn_num_temp['state'] = 'disabled'

        if self.opnum == 24:
            self.label_ans['text'] = 'right'

    def command_numwhich(self, num, btn_num):
        if self.op_pressed:
            self.opnum = self.opdict[self.op_now](self.opnum, num)[0]
            if not self.btn_num_temp_used:
                self.btn_num_temp['text'] = self.opnum
                self.num_temp = self.opnum
                self.btn_num_temp_used = True
        else:
            self.opnum = num
        print(self.opnum)
        self.op_pressed = False
        btn_num['state'] = 'disabled'
        self.op_can_use = True
        self.num_count += 1
        if self.opnum == 24 and self.num_count ==4:
            self.label_ans['text'] = 'right' 

    def command_num1(self):
        return self.command_numwhich(self.num1, self.btn_num1)

    def command_num2(self):
        return self.command_numwhich(self.num2, self.btn_num2)

    def command_num3(self):
        return self.command_numwhich(self.num3, self.btn_num3)

    def command_num4(self):
        return self.command_numwhich(self.num4, self.btn_num4)

    def center(self):
        ws = self.tkwindow.winfo_screenwidth()
        hs = self.tkwindow.winfo_screenheight()
        x = int((ws/2)-(self.w/2))
        y = int((hs/2)-(self.h/2))
        self.tkwindow.geometry('{}x{}+{}+{}'.format(self.w, self.h, x, y))

    def loop(self):
        self.tkwindow.resizable(False, False)
        self.center()
        self.tkwindow.mainloop()

# ##############################run##################################
w = Window()
w.loop()

 

 

 

# encoding:utf-8
# file point24/bk

import itertools
import random

def add(a, b):
    return a+b, str(a)+'+'+str(b)+'='+str(a+b)

def minus(a, b):
    # 打印答案时不要有负数
    if a<b:
        return 9999, 'no'
    return a-b, str(a)+'-'+str(b)+'='+str(a-b)

def multiply(a, b):
    return a*b, str(a)+'*'+str(b)+'='+str(a*b)

def divide(a, b):
    if b == 0:
        return 9999, 'no'
    return a/b, str(a)+'/'+str(b)+'='+str(a/b)


def cal_24point(a, b, c, d):
    # a, b, c, d的排列组合
    permutation_list = list(itertools.permutations([a, b, c, d], 4))  
    # 加减乘除 排列组合
    op_list = list(itertools.permutations([add, minus, multiply, divide], 4))  
    
    # pro1 到 pro5包装函数
    # ((a, b), c), d
    def pro1(op1, op2, op3):
        m = op1(pmt[0], pmt[1])
        n = op2(m[0], pmt[2])
        result = op3(n[0], pmt[3])
        if result[0] == 24:
            #print(m[1], n[1], result[1])
            return (m[1], n[1], result[1])
    
    # (c, (a, b)), d    
    def pro2(op1, op2, op3):
        m = op1(pmt[0], pmt[1])
        n = op2(pmt[2] , m[0])
        result = op3(n[0], pmt[3])
        if result[0] == 24:
            #print(m[1], n[1], result[1])
            return (m[1], n[1], result[1])

    # d, ((a, b), c)
    def pro3(op1, op2, op3):
        m = op1(pmt[0], pmt[1])
        n = op2(m[0], pmt[2])
        result = op3(pmt[3], n[0])
        if result[0] == 24:
            #print(m[1], n[1], result[1])
            return (m[1], n[1], result[1])

    # d, (c, (a, b))
    def pro4(op1, op2, op3):
        m = op1(pmt[0], pmt[1])
        n = op2(pmt[2], m[0])
        result = op3(pmt[3], n[0])
        if result[0] == 24:
            #print(m[1], n[1], result[1])
            return (m[1], n[1], result[1]) 

    # (a b)(c d)
    def pro5(op1, op2, op3):
        m = op1(pmt[0], pmt[1])
        n = op2(pmt[2], pmt[3])
        result = op3(n[0], m[0])
        if result[0] == 24:
            #print(m[1], n[1], result[1])
            return (m[1], n[1], result[1])

    for pmt in permutation_list:
        for op in op_list:
            # 相同运算符
            if pro1(op[0], op[0], op[0]):
                return pro1(op[0], op[0], op[0])
            if pro2(op[0], op[0], op[0]):
                return pro2(op[0], op[0], op[0])
            if pro3(op[0], op[0], op[0]):
                return pro3(op[0], op[0], op[0])
            if pro4(op[0], op[0], op[0]):
                return pro4(op[0], op[0], op[0])
            if pro5(op[0], op[0], op[0]):
                return pro5(op[0], op[0], op[0])

            # ((a, b), c), d
            if pro1(op[0], op[1], op[2]):
                return pro1(op[0], op[1], op[2])
            if pro1(op[0], op[1], op[1]):
                return pro1(op[0], op[1], op[1])
            if pro1(op[0], op[0], op[1]):
                return pro1(op[0], op[0], op[1])
            if pro1(op[0], op[1], op[0]):
                return pro1(op[0], op[1], op[0])

            # (c, (a, b)), d
            if pro2(op[0], op[1], op[2]):
                return pro2(op[0], op[1], op[2])
            if pro2(op[0], op[1], op[1]):
                return pro2(op[0], op[1], op[1])
            if pro2(op[0], op[0], op[1]):
                return pro2(op[0], op[0], op[1])
            if pro2(op[0], op[1], op[0]):
                return pro2(op[0], op[1], op[0])

            # d, ((a, b), c)
            if pro3(op[0], op[1], op[2]):
                return pro3(op[0], op[1], op[2])
            if pro3(op[0], op[1], op[1]):
                return pro3(op[0], op[1], op[1])
            if pro3(op[0], op[0], op[1]):
                return pro3(op[0], op[0], op[1])
            if pro3(op[0], op[1], op[0]):
                return pro3(op[0], op[1], op[0])

            # d, (c, (a, b))
            if pro4(op[0], op[1], op[2]):
                return pro4(op[0], op[1], op[2])
            if pro4(op[0], op[1], op[1]):
                return pro4(op[0], op[1], op[1])
            if pro4(op[0], op[0], op[1]):
                return pro4(op[0], op[0], op[1])
            if pro4(op[0], op[1], op[0]):
                return pro4(op[0], op[1], op[0])

            # (a b)(c d)
            if pro5(op[0], op[1], op[2]):
                return pro5(op[0], op[1], op[2])
            if pro5(op[0], op[1], op[1]):
                return pro5(op[0], op[1], op[1])
            if pro5(op[0], op[0], op[1]):
                return pro5(op[0], op[0], op[1])
            if pro5(op[0], op[1], op[0]):
                return pro5(op[0], op[1], op[0])
    print('no result')
    return None


# ---------------------------test---------------------------------
'''

for n in range(30):
    a = random.randint(1,13)
    b = random.randint(1,13)
    c = random.randint(1,13)
    d = random.randint(1,13)
    print(a, b, c, d)
    print(cal_24point(a, b, c, d),'*'*10)
'''

 

 界面是难看了点 ,哈哈哈哈



 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值