Python必备封装基本代码~Python函数

简介: Python必备封装基本代码~Python函数

大家好,我是辣条

最近不少粉丝通过文末找到辣条让我分享一些代码封装这一块的内容,今天他来了~
一遍看不懂就收起来慢慢看,我写的还是很详细的,一定是能轻松拿捏住Python函数的,不过还请记得多多支持辣条,码字不易~

目录
1.如何用函数
2.默认参数陷阱
2.1针对可变数据类型,不可变不受影响
3.名称空间和作用域
4闭包函数:
5函数的参数
5.1定义阶段
5.2调用阶段
6.装饰器:闭包函数的应用
6.1装饰器的实现必须遵循两大原则:
6.2装饰器语法糖
6.3无参装饰器
6.4有参装饰器
7.题目
1.如何用函数
​ 先定义后调用,定义阶段只检测语法,不执行代码
调用阶段,开始执行代码
函数都有返回值
定义时无参,调用时也是无参
定义时有参,调用时也必须有参

2.默认参数陷阱
2.1针对可变数据类型,不可变不受影响
def c(a=[]):

a.append(1)
print(a)

c()
c()
c()
结果:
[1]
[1, 1]
[1, 1, 1]
1
2
3
4
5
6
7
8
9
10
def c(a=[]):

a.append(1)
print(a)

c([])
c([])
c([])
结果:
[1]
[1]
[1]
1
2
3
4
5
6
7
8
9
10
3.名称空间和作用域
​ 名称空间就是用来存放名字与值内存地址绑定关系的地方(内存空间)
但凡查找值一定要通过名字,访问名字必须去查找名称空间
名称空间分为三大类
内置名称空间: 存放的是python解释器自带的名字
生命周期: 在解释器启动时则生效,解释器关闭则失效
全局名称空间: 存放的是文件级别的名字
生命周期: 在解释器解释执行python文件时则生效,文件执行完毕后则失效
局部名称空间: 在函数内定义的名字
生命周期: 只在调用函数时临时产生该函数的局部名称空间,该函数调用完毕则失效
加载顺序
内置->全局->局部
查找名字的顺序
基于当前所在位置往上查找
假设当前站在局部,查找顺序:局部->全局->内置
假设当前站在全局,查找顺序:全局->内置
名字的查找顺序,在函数定义阶段就已经固定死了(即在检测语法时就已经确定了名字的查找顺序),与函数的调用位置无关

也就是说无论在任何地方调用函数,都必须回到当初定义函数的位置去确定名字的查找关系

作用域: 作用域指的就是作用的范围
全局作用域: 包含的是内置名称空间与全局名称空间中的名字
特点: 全局有效,全局存活
局部作用域: 包含的是局部名称空间中的名字
特点: 局部有效,临时存活
global: 在局部声明一个名字是来自于全局作用域的,可以用来在局部修改全局的不可变类型
nonlocal: 声明一个名字是来自于当前层外一层作用域的,可以用来在局部修改外层函数的不可变类型

4闭包函数:
定义在函数内部且包含对外部函数的作用域名字的引用,需要结合函数对象的概念将闭包函数返回到全局作用域去使用,从而打破函数的层级限制
闭包函数提供了一种为函数体传值的解决方案

def func():

name='egon'
def inner():
    print(name)
return inner

inner = func()
inner()
1
2
3
4
5
6
7
5函数的参数
5.1定义阶段
​ 位置形参
在定义阶段从左往右的顺序依次定义的形参
默认形参
在定义阶段已经为其初始化赋值
关键字参数
自由主题
可变长度的形参args
溢出的位置参数,打包成元组,给接受,赋给args的变量名
命名关键字参数
放在*和之间的参数,必须按照key=value形式传值
可变长度的位置形参kwargs
溢出的关键字实参,打包成字典,给**接受,赋给变量kwargs
形参和实参关系: 在调用函数时,会将实参的值绑定给形参的变量名,这种绑定关系临时生效,在调用结束后就失效了

5.2调用阶段
​ 位置实参
调用阶段按照从左往右依次传入的传入的值,会与形参一一对应
关键字实参
在调用阶段,按照key=value形式指名道姓的为形参传值
实参中带*的,再传值前先将打散成位置实参,再进行赋值
实参中带的**,在传值前先将其打散成关键字实参,再进行赋值

6.装饰器:闭包函数的应用

装饰器就是用来为被装饰器对象添加新功能的工具
注意:装饰器本身可以是任意可调用对象,被装饰器的对象也可以是任意可调用对象
为何使用装饰器
开放封闭原则:封闭指的是对修改封闭,对扩展开放

6.1装饰器的实现必须遵循两大原则:
​ 1. 不修改被装饰对象的源代码`

  1. 不修改被装饰器对象的调用方式

装饰器的目标:就是在遵循1和2原则的前提下为被装饰对象添加上新功能

6.2装饰器语法糖
在被装饰对象正上方单独一行写@装饰器的名字
python解释器一旦运行到@装饰器的名字,就会调用装饰器,然后将被装饰函数的内存地址当作参数传给装饰器,最后将装饰器调用的结果赋值给原函数名 foo=auth(foo) 此时的foo是闭包函数wrapper

6.3无参装饰器
import time
def timmer(func):

def wrapper(*args,**kwargs):
    start_time=time.time()
    res=func(*args,**kwargs)
    stop_time=time.time()
    print('run time is %s' %(stop_time-start_time))
    return res
return wrapper

@timmer
def foo():

time.sleep(3)
print('from foo')

foo()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
6.4有参装饰器
def auth(driver='file'):

def auth2(func):
    def wrapper(*args,**kwargs):
        name=input("user: ")
        pwd=input("pwd: ")

    if driver == 'file':
        if name == 'egon' and pwd == '123':
            print('login successful')
            res=func(*args,**kwargs)
            return res
    elif driver == 'ldap':
        print('ldap')
return wrapper

return auth2

@auth(driver='file')
def foo(name):

print(name)

foo('egon')

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
7.题目

题目一:

db='db.txt'
login_status={'user':None,'status':False}
def auth(auth_type='file'):

def auth2(func):
    def wrapper(*args,**kwargs):
        if login_status['user'] and login_status['status']:
            return func(*args,**kwargs)
        if auth_type == 'file':
            with open(db,encoding='utf-8') as f:
                dic=eval(f.read())
            name=input('username: ').strip()
            password=input('password: ').strip()
            if name in dic and password == dic[name]:
                login_status['user']=name
                login_status['status']=True
                res=func(*args,**kwargs)
                return res
            else:
                print('username or password error')
        elif auth_type == 'sql':
            pass
        else:
            pass
    return wrapper
return auth2

@auth()
def index():

print('index')

@auth(auth_type='file')
def home(name):

print('welcome %s to home' %name)

index()

home('egon')

题目二

import time,random
user={'user':None,'login_time':None,'timeout':0.000003,}

def timmer(func):

def wrapper(*args,**kwargs):
    s1=time.time()
    res=func(*args,**kwargs)
    s2=time.time()
    print('%s' %(s2-s1))
    return res
return wrapper

def auth(func):

def wrapper(*args,**kwargs):
    if user['user']:
        timeout=time.time()-user['login_time']
        if timeout < user['timeout']:
            return func(*args,**kwargs)
    name=input('name>>: ').strip()
    password=input('password>>: ').strip()
    if name == 'egon' and password == '123':
        user['user']=name
        user['login_time']=time.time()
        res=func(*args,**kwargs)
        return res
return wrapper

@auth
def index():

time.sleep(random.randrange(3))
print('welcome to index')

@auth
def home(name):

time.sleep(random.randrange(3))
print('welcome %s to home ' %name)

index()
home('egon')

题目三:简单版本

import requests
import os
cache_file='cache.txt'
def make_cache(func):

def wrapper(*args,**kwargs):
    if not os.path.exists(cache_file):
        with open(cache_file,'w'):pass

    if os.path.getsize(cache_file):
        with open(cache_file,'r',encoding='utf-8') as f:
            res=f.read()
    else:
        res=func(*args,**kwargs)
        with open(cache_file,'w',encoding='utf-8') as f:
            f.write(res)
    return res
return wrapper

@make_cache
def get(url):

return requests.get(url).text

res=get('https://www.python.org')

print(res)

题目四:扩展版本

import requests,os,hashlib
engine_settings={

'file':{'dirname':'./db'},
'mysql':{
    'host':'127.0.0.1',
    'port':3306,
    'user':'root',
    'password':'123'},
'redis':{
    'host':'127.0.0.1',
    'port':6379,
    'user':'root',
    'password':'123'},

}

def make_cache(engine='file'):

if engine not in engine_settings:
    raise TypeError('egine not valid')
def deco(func):
    def wrapper(url):
        if engine == 'file':
            m=hashlib.md5(url.encode('utf-8'))
            cache_filename=m.hexdigest()
            cache_filepath=r'%s/%s' %(engine_settings['file']['dirname'],cache_filename)

            if os.path.exists(cache_filepath) and os.path.getsize(cache_filepath):
                return open(cache_filepath,encoding='utf-8').read()

            res=func(url)
            with open(cache_filepath,'w',encoding='utf-8') as f:
                f.write(res)
            return res
        elif engine == 'mysql':
            pass
        elif engine == 'redis':
            pass
        else:
            pass

    return wrapper
return deco

@make_cache(engine='file')
def get(url):

return requests.get(url).text

print(get('https://www.python.org'))

print(get('https://www.baidu.com'))

题目五

route_dic={}

def make_route(name):

def deco(func):
    route_dic[name]=func
return deco

@make_route('select')
def func1():

print('select')

@make_route('insert')
def func2():

print('insert')

@make_route('update')
def func3():

print('update')

@make_route('delete')
def func4():

print('delete')

print(route_dic)

题目六

import time
import os

def logger(logfile):

def deco(func):
    if not os.path.exists(logfile):
        with open(logfile,'w'):pass

    def wrapper(*args,**kwargs):
        res=func(*args,**kwargs)
        with open(logfile,'a',encoding='utf-8') as f:
            f.write('%s %s run\n' %(time.strftime('%Y-%m-%d %X'),func.__name__))
        return res
    return wrapper
return deco

@logger(logfile='aaaaaaaaaaaaaaaaaaaaa.log')
def index():

print('index')

index()

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208

目录
相关文章
|
19天前
|
开发者 Python
Python入门:8.Python中的函数
### 引言 在编写程序时,函数是一种强大的工具。它们可以将代码逻辑模块化,减少重复代码的编写,并提高程序的可读性和可维护性。无论是初学者还是资深开发者,深入理解函数的使用和设计都是编写高质量代码的基础。本文将从基础概念开始,逐步讲解 Python 中的函数及其高级特性。
Python入门:8.Python中的函数
|
11天前
|
C语言 Python
Python学习:内建属性、内建函数的教程
本文介绍了Python中的内建属性和内建函数。内建属性包括`__init__`、`__new__`、`__class__`等,通过`dir()`函数可以查看类的所有内建属性。内建函数如`range`、`map`、`filter`、`reduce`和`sorted`等,分别用于生成序列、映射操作、过滤操作、累积计算和排序。其中,`reduce`在Python 3中需从`functools`模块导入。示例代码展示了这些特性和函数的具体用法及注意事项。
|
11天前
|
Go Python
Python中的round函数详解及使用示例
`round()`函数是Python内置的用于四舍五入数字的工具。它接受一个数字(必需)和可选的小数位数参数,返回最接近的整数或指定精度的浮点数。本文详细介绍其用法、参数及示例,涵盖基本操作、负数处理、特殊情况及应用建议,帮助你更好地理解和运用该函数。
|
11天前
|
数据采集 供应链 API
实战指南:通过1688开放平台API获取商品详情数据(附Python代码及避坑指南)
1688作为国内最大的B2B供应链平台,其API为企业提供合法合规的JSON数据源,直接获取批发价、SKU库存等核心数据。相比爬虫方案,官方API避免了反爬严格、数据缺失和法律风险等问题。企业接入1688商品API需完成资质认证、创建应用、签名机制解析及调用接口四步。应用场景包括智能采购系统、供应商评估模型和跨境选品分析。提供高频问题解决方案及安全合规实践,确保数据安全与合法使用。立即访问1688开放平台,解锁B2B数据宝藏!
|
11天前
|
API 开发工具 Python
【Azure Developer】编写Python SDK代码实现从China Azure中VM Disk中创建磁盘快照Snapshot
本文介绍如何使用Python SDK为中国区微软云(China Azure)中的虚拟机磁盘创建快照。通过Azure Python SDK的Snapshot Class,指定`location`和`creation_data`参数,使用`Copy`选项从现有磁盘创建快照。代码示例展示了如何配置Default Azure Credential,并设置特定于中国区Azure的`base_url`和`credential_scopes`。参考资料包括官方文档和相关API说明。
|
2月前
|
存储 缓存 Java
Python高性能编程:五种核心优化技术的原理与Python代码
Python在高性能应用场景中常因执行速度不及C、C++等编译型语言而受质疑,但通过合理利用标准库的优化特性,如`__slots__`机制、列表推导式、`@lru_cache`装饰器和生成器等,可以显著提升代码效率。本文详细介绍了这些实用的性能优化技术,帮助开发者在不牺牲代码质量的前提下提高程序性能。实验数据表明,这些优化方法能在内存使用和计算效率方面带来显著改进,适用于大规模数据处理、递归计算等场景。
80 5
Python高性能编程:五种核心优化技术的原理与Python代码
|
12天前
|
人工智能 数据库连接 开发工具
[oeasy]python069_当前作用域都有些什么_列表dir_函数_builtins
本文介绍了Python中`dir()`函数的使用方法及其作用。`dir()`可以列出当前作用域内的所有变量和成员,类似于`locals()`,但`dir()`不仅限于本地变量,还能显示模块中的所有成员。通过`dir(__builtins__)`可以查看内建模块中的所有内建函数,如`print`、`ord`、`chr`等。此外,还回顾了`try-except-finally`结构在数据库连接中的应用,并解释了为何`print`函数可以直接使用而无需导入,因为它位于`__builtins__`模块中。最后,简要提及了删除`__builtins__.print`的方法及其影响。
26 0
|
3月前
|
Python
课程设计项目之基于Python实现围棋游戏代码
游戏进去默认为九路玩法,当然也可以选择十三路或是十九路玩法 使用pycharam打开项目,pip安装模块并引用,然后运行即可, 代码每行都有详细的注释,可以做课程设计或者毕业设计项目参考
86 33
|
2月前
|
Python
[oeasy]python057_如何删除print函数_dunder_builtins_系统内建模块
本文介绍了如何删除Python中的`print`函数,并探讨了系统内建模块`__builtins__`的作用。主要内容包括: 1. **回忆上次内容**:上次提到使用下划线避免命名冲突。 2. **双下划线变量**:解释了双下划线(如`__name__`、`__doc__`、`__builtins__`)是系统定义的标识符,具有特殊含义。
37 3
|
3月前
|
JavaScript API C#
【Azure Developer】Python代码调用Graph API将外部用户添加到组,结果无效,也无错误信息
根据Graph API文档,在单个请求中将多个成员添加到组时,Python代码示例中的`members@odata.bind`被错误写为`members@odata_bind`,导致用户未成功添加。
61 10

热门文章

最新文章