一、闭包函数#快速的定制函数

函数内部函数对外部作用域而非全局作用域的引用。

内部函数引用了外部函数的变量

外部函数返回内部函数(或将其传递出去)

def f1(int):
    def f2():
        pass
    return f2

返回的函数对象,不仅仅是一个函数对象,在该函数外还包裹了一层作用域,这使得,该函数无论在何处调用,优先使用自己外层包裹的作用域。

计数器

def counter():  # 外部函数
    count = 0   # 被闭包"记住"的变量
    
    def increment():  # 内部函数(闭包)
        nonlocal count
        count += 1
        return count
    
    return increment  # 返回内部函数

# 使用闭包
c = counter()
print(c())  # 输出: 1
print(c())  # 输出: 2 (记住上次的 count 值)
1
2

快速定制函数

def multiplier(factor):  # 外部函数接受参数
    def multiply(x):     # 闭包捕获外部参数 factor
        return x * factor
    return multiply

# 创建定制化闭包
double = multiplier(2)
triple = multiplier(3)

print(double(5))  # 输出: 10(5*2)
print(triple(5))  # 输出: 15(5*3)

二、装饰器#具有装饰功能的函数

改变功能的时候不改变原来的调用方式,并且改变原来函数的代码

import time

def sleep(int):
    time.sleep(int)

def timetest(func):
    def f1(i):
        x=time.time()
        func(i)
        y=time.time()
        print(y-x)
    return f1
sleep_time = timetest(sleep)
sleep_time(6)
6.0010902881622314

装饰器模板

def outter(func):
    def wrapper(*args,**kwargs):
        res = func(*args,**kwargs)
        return res
    return wrapper
    

语法糖 @

import time

def timetest(func):
    def f1(i):
        x=time.time()
        func(i)
        y=time.time()
        print(y-x)
    return f1
    
@timetest #sleep_time = timetest(sleep)

def sleep(int):
    time.sleep(int)
sleep_time(6)
6.001430511474609

三层装饰器 #给装饰器传参

def f(x):
    def outter(func):
        def wrapper(*args,**kwargs):
            res = func(*args,**kwargs)
            return res
        return wrapper
    return outter

demo = f(x)
pl = demo(func)
pl()

目录导航

menu = {
    '北京': {
        '海淀': {
            '五道口': {
                'soho': {},
                '网易': {},
                'google': {}
            },
            '中关村': {
                '爱奇艺': {},
                '汽车之家': {},
                'youku': {},
            },
            '上地': {
                '百度': {},
            },
        },
        '昌平': {
            '沙河': {
                '老男孩': {},
                '北航': {},
            },
            '天通苑': {},
            '回龙观': {},
        },
        '朝阳': {},
        '东城': {},
    },
    '上海': {
        '闵行': {
            "人民广场": {
                '炸鸡店': {}
            }
        },
        '闸北': {
            '火车战': {
                '携程': {}
            }
        },
        '浦东': {},
    },
    '山东': {},
}

tag = True
while tag:
    menu1 = menu
    for key in menu1:  # 打印第一层
        print(key)

    choice1 = input('第一层>>: ').strip()  # 选择第一层

    if choice1 == 'b':  # 输入b,则返回上一级
        break
    if choice1 == 'q':  # 输入q,则退出整体
        tag = False
        continue
    if choice1 not in menu1:  # 输入内容不在menu1内,则继续输入
        continue

    while tag:
        menu_2 = menu1[choice1]  # 拿到choice1对应的一层字典
        for key in menu_2:
            print(key)

        choice2 = input('第二层>>: ').strip()

        if choice2 == 'b':
            break
        if choice2 == 'q':
            tag = False
            continue
        if choice2 not in menu_2:
            continue

        while tag:
            menu_3 = menu_2[choice2]
            for key in menu_3:
                print(key)

            choice3 = input('第三层>>: ').strip()
            if choice3 == 'b':
                break
            if choice3 == 'q':
                tag = False
                continue
            if choice3 not in menu_3:
                continue

            while tag:
                menu_4 = menu_3[choice3]
                for key in menu_4:
                    print(key)

                choice4 = input('第四层>>: ').strip()
                if choice4 == 'b':
                    break
                if choice4 == 'q':
                    tag = False
                    continue
                if choice4 not in menu_4:
                    continue

                # 第四层内没数据了,无需进入下一层
北京
上海
山东


第一层>>:  q
menu = {
    '北京': {
        '海淀': {
            '五道口': {
                'soho': {},
                '网易': {},
                'google': {}
            },
            '中关村': {
                '爱奇艺': {},
                '汽车之家': {},
                'youku': {},
            },
            '上地': {
                '百度': {},
            },
        },
        '昌平': {
            '沙河': {
                '老男孩': {},
                '北航': {},
            },
            '天通苑': {},
            '回龙观': {},
        },
        '朝阳': {},
        '东城': {},
    },
    '上海': {
        '闵行': {
            "人民广场": {
                '炸鸡店': {}
            }
        },
        '闸北': {
            '火车战': {
                '携程': {}
            }
        },
        '浦东': {},
    },
    '山东': {},
}
trigge = 1
print('b:back,q:quit')
while trigge:
    for i in menu:
        print(i)
    choice1 = input('选择路径').strip()
    if choice1 == 'q':
        break
    elif choice1 not in menu:
        continue
    menu_1 = menu[choice1]
    while trigge:
        for i in menu_1:
            print(i)
        choice2 = input('选择路径').strip()
        if choice2 == 'b':
            break
        elif choice2 == 'q':
            trigge = 0
            break
        elif choice2 not in menu_1:
            continue
        menu_2 = menu_1[choice2]
        while trigge:
            for i in menu_2:
                print(i)
            choice3 = input('选择路径').strip()
            if choice3 == 'b':
                break
            elif choice3 == 'q':
                trigge = 0
                break
            elif choice3 not in menu_2:
                continue
            menu_3 = menu_2[choice3]
            while trigge:
                for i in menu_3:
                    print(i)
                choice4 = input('选择路径').strip()
                if choice4 == 'b':
                    break
                elif choice4 == 'q':
                    trigge = 0
                    break
                elif choice4 not in menu_3:
                    continue
                while trigge:
                    print('已是最后一级')
                    choice5 = input('退出?')
                    if choice4 == 'b':
                        break
                    elif choice4 == 'q':
                        trigge = 0
                    continue
b:back,q:quit
北京
上海
山东


选择路径 北京


海淀
昌平
朝阳
东城


选择路径 海淀


五道口
中关村
上地


选择路径 五道口


soho
网易
google


选择路径 soho


已是最后一级


退出? b


soho
网易
google


选择路径 b


五道口
中关村
上地


选择路径 b


海淀
昌平
朝阳
东城


选择路径 b


北京
上海
山东


选择路径 


北京
上海
山东


选择路径 q
menu = {
    '北京': {
        '海淀': {
            '五道口': {'soho': {}, '网易': {}, 'google': {}},
            '中关村': {'爱奇艺': {}, '汽车之家': {}, 'youku': {}},
            '上地': {'百度': {}},
        },
        '昌平': {
            '沙河': {'老男孩': {}, '北航': {}},
            '天通苑': {},
            '回龙观': {},
        },
        '朝阳': {},
        '东城': {},
    },
    '上海': {
        '闵行': {"人民广场": {'炸鸡店': {}}},
        '闸北': {'火车战': {'携程': {}}},
        '浦东': {},
    },
    '山东': {},
}

def navigate_menu(current_data):
    """
    一个可以导航任何一层菜单的递归函数。
    它会返回一个状态:'quit' 表示需要退出,其他情况正常返回。
    """
    while True:
        if not current_data:
            print("---- 已是最后一级,输入 'b' 返回 ----")
        else:
            for key in current_data:
                print(key)
        
        print("\n提示: 输入 'b' 返回上一级, 输入 'q' 退出程序。")
        choice = input("请选择您的路径 > ").strip()

        if choice == 'b':
            # 返回上一层,函数正常结束,无需返回特殊状态
            return

        elif choice == 'q':
            # 用户想退出,返回一个'quit'信号
            return 'quit'

        elif choice in current_data:
            # --- 递归调用,并捕获其返回值 ---
            next_level_data = current_data[choice]
            status = navigate_menu(next_level_data)

            # --- 关键部分:信号传递 ---
            # 如果下一层函数返回了'quit'信号,本层函数也必须立即返回'quit'
            # 这样才能把退出信号一路传到最顶层
            if status == 'quit':
                return 'quit'
            
        else:
            print("---- 输入无效,请重新选择! ----")


# --- 程序开始 ---
print("欢迎来到多级菜单系统!")
# 我们在最外层调用函数,并检查最终的返回状态
final_status = navigate_menu(menu)

if final_status == 'quit':
    print("程序已退出。")

# 当程序执行到这里时,脚本会自然结束,不会再有输入提示。
欢迎来到多级菜单系统!
北京
上海
山东

提示: 输入 'b' 返回上一级, 输入 'q' 退出程序。


请选择您的路径 >  北京


海淀
昌平
朝阳
东城

提示: 输入 'b' 返回上一级, 输入 'q' 退出程序。


请选择您的路径 >  海淀


五道口
中关村
上地

提示: 输入 'b' 返回上一级, 输入 'q' 退出程序。


请选择您的路径 >  五道口


soho
网易
google

提示: 输入 'b' 返回上一级, 输入 'q' 退出程序。


请选择您的路径 >  soho


---- 已是最后一级,输入 'b' 返回 ----

提示: 输入 'b' 返回上一级, 输入 'q' 退出程序。


请选择您的路径 >  q


程序已退出。

购物车系统

product_list = [
    ['Iphone7', 5800],
    ['Coffee', 30],
    ['疙瘩汤', 10],
    ['Python Book', 99],
    ['Bike', 199],
    ['ViVo X9', 2499],
]
def denglu():
    user_info_dict = {}
    while 1:
        with open(r'D:/桌面/user_info.txt','r',encoding='utf-8') as fr:
            for i in fr:
                name = i.split(':')[0]
                user_info_dict[name] = i.split(':')[1][:4]
        user = input('请输入你的账号:').strip()
        if user in user_info_dict:
            password = input('请输入四位密码:')
            if user_info_dict[user] == password:
                print(f'{user} 欢迎')
                return user
                break
        else :
            buch = input('没有搜索到该账号,是否要注册Y&N ?')
            if buch == 'Y':
                while 1:
                    new_password = input('请输入四位密码')
                    new_password1 = input('再次输入以确认')
                    if new_password == new_password1:
                        break
                    print('两次输入不一致!')
                with open(r'D:/桌面/user_info.txt','a',encoding='utf-8') as fa:
                    fa.write(f'\n{user}:{new_password}')
                print('注册成功!')
            elif buch == 'N':
                continue
user = denglu()
tatal = int(input('今天想消费多少钱?').strip())
tatal0 = tatal
shopping_dict = {}
print(f'尊敬的用户{user},您的余额为{tatal}元,祝您购物愉快!')
product_dict = {}
j=0
for i in product_list:
    j+=1
    product_dict[str(j)] = i
print(product_dict)
while 1:
    choice1 = input('你想买什么?(输入q退出)').strip()
    if choice1 in product_dict:
        num1 = int(input('买多少?').strip())
        tatal1 = tatal - num1*product_dict[choice1][1]
        if tatal1 < 0:
            print('钱不够')
        else:
            if choice1 not in shopping_dict:
                shopping_dict[product_dict[choice1][0]] = num1
            else:
                shopping_dict[product_dict[choice1][0]] += num1
            tatal = tatal1
            print(f'你还剩{tatal}元')
    elif choice1 == 'q':
        print(f'''
        您购买的商品列表
        {product_dict}
        你共消费{tatal0-tatal}元
        您的余额为{tatal}元
        欢迎下次再来
        ''')
        break
    else:
        print('没有该商品')

posted on 2025-07-18 13:48  新月绘影  阅读(6)  评论(0)    收藏  举报