周结
文件操作
文件:操作系统提供给用户可以直接操作硬盘的快捷方式
代码打开文件的方式:
1.
f = open ( 文件路径, 读写模式, encoding= 'utf8' )
f. close( )
2.
with open ( r'a.txt' , 'r' , encoding= 'utf8' ) as f:
with 子代码
with 能够在文件运行结束完自动用close关闭资源
为了解斜杠在字母中的组合会产生特殊含义可以在字符串的路径前面加字母r
with 支持一次性打开多个文件
with open ( ) as f1, open ( ) as f2, open ( ) as f3:
子代码
pass . . . 都快可以补全语法结构 不执行功能 本身没有任何意义
文件读写模式
'r' 只读模式:只能读不能写 文件路径不存在会直接报错
'w' 只写模式:只能写不能看 文件路径不存在会自动创建 文件路径存在会先清空文件内容 之后再写入
'a' 只追加模式 文件末尾添加数据 文件路径不存在 自动创建 文件路径存在自动在末尾等待追加内容
文件操作模式
't' 文本模式
默认的模式 r w a 其实就是rt wt at
是只能操作文本文件
读写都是以字符为单位
要指定encoding参数 如果没指定 会采用计算机默认的编码
'b' 二进制模式( bytes 模式)
不是默认的模式 需要自己指定 rb wb ab
是可以操作任意文件
读写都是以bytes 为单位
不需要指定encoding参数
文件中的方法
1 . read( )
一次性读取文件中的内容 并且光标停留在文件的末尾 所以反复的读取是读不到的
当文件内容过多时该方法可能会导致计算机内存溢出
括号内还可以填写数字 在文本模式下 表示读取的几个字符
2. for 循环
一次性读取文件内容 避免内存溢出现象的产生
3 . readline( )
一次只读一行内容
4 . readlines( )
一次性读取文件内容 会按照行数组织成列表的一个个数据值
5 . readable( )
判断具备是否读写数据的能力
6 . write( )
写入数据
7 . writeable( )
判断文件是否具备写数据的能力
8 . writelines( )
接收一个列表 一次性将列表中所用的数据值写入
9 . flush( )
将文件数据保存到硬盘 相当于ctrl + s
光标的移动
seek( 位移量, 模式)
位移量是以字节为单位
模式 0 1 2 't' 文本模式只能用0 模式 而二进制'b' 模式0 1 2 模式都可以使用
0 是基于文件开头
1 是基于当前位置
2 是基于文件末尾
函数的语法结构
函数:是相同代码在不同位置反复执行 它类似于提准备好的工具 什么时候想用就直接拿出来用
语法结构:
def 函数名( ) :
'''函数注释'''
函数体代码
return 返回值
函数在定义阶段只检测语法不执行函数体代码
函数分:空函数 无参函数 有参函数
返回值return :是调用函数给调用者的结果 是可选的可写可不写
变量名 = 函数名加括号 先执行函数体代码 然后将返回值赋值给变量名
return 后面跟什么就返回什么
如果没写就默认返回None
return 后面如果跟了多个数据值 则自动组织成元组返回
且函数体代码遇到return 会立刻结束
函数的参数:
在函数定义阶段括号内填写的参数 简称'形参'
在函数调用阶段括号内填写的参数 简称'实参'
他们的关系:
形参就好比是变量名 在函数定义阶段时 可以随便写 但要遵循见名知意
实参就好比是数据值 在函数调用阶段时与形参做临时绑定 在运行结束时 函数运行结束时立刻断开
函数参数之位置参数
位置形参:函数定义阶段内从左往右依次填写的变量名
位置实参:函数在调用阶段括号内从左往右一次填写的数据值
是按照位置一一传值 少一个不行多一个也不行 关键字传参一定要跟在位置参数的后面 同一个形参再调用的时候不能被多次赋值
默认参数
本质就是关键字形参
就是提前就已经定义好了 用户可以传 也可以不传
同样遵循越短越简单的越靠前 长越复杂的越靠后
def user ( name, gender= male) :
print ( name, gender)
user( 'jason' )
user( 'jason' , 'female' )
可变长参数
'*' 用于接收多余的位置参数组织成元组的形式赋值给* 号后面的变量名
def index ( * a) :
print ( a)
index( 1 , 2 , 3 , 4 , 5 )
'**' 用于接收多余的关键字参数组织成字典的形式赋值给** 号后面的变量名
def index ( ** a) :
print ( a)
index( a= 1 , b= 2 , c= 3 )
后面跟的变量名推介使用
* args
** kwargs
'*' 类似于for 循环 将所有循环遍历出来的数据按照位置参数一次性传给函数
l1 = [ 22 , 44 , 55 ]
def index ( a, b, c) :
print ( a, b, c)
index( * l1)
'**' 将字典打散成关键字的形式传递给函数
l2 = { 'a' : 'jason' , 'b' : 13 , 'c' : 123 }
def index ( a, b, c) :
print ( a, b, c)
index( ** l2)
名称空间
就是用来存储变量名与数据值绑定关系的地方 就是存储变量名的地方
内置名称空间:解释器运行产生 python解释器启动则创建 关闭则销毁
全局名称空间:py文件运行产生 py文件级别全局有效
局部名称空间:函数体代码运行 函数体代码内有效
当在局部名称空间的时候:
局部名称空间——> 全局名称空间——> 内置名称空间
当在全局名称空间的时候:
全局名称空间——> 内置名称空间
但也是可以打破的:
global 局部修改全局名称空间中的数据
name = 'jason'
def fucn ( ) :
global name
name = 'kevin'
func( )
print ( name)
nonlocal 内层局部修改外层局部名称空间中的数据
def index ( ) :
name = 'oscar'
def outer ( ) :
nonlocal name
name = 'lili'
outer( )
print ( name)
函数名的多种用法
1. 可以当做变量名
def index ( ) :
print ( 'index' )
res = index
res( )
2. 可以当做函数的参数进行传参
def index ( ) :
print ( 'index' )
def func ( a) :
a( )
func( index)
3. 可以当做函数的返回值
def index ( ) :
print ( 'index' )
def func ( ) :
print ( 'func' )
return index
res = func( )
res( )
4. 可以当做是容器类型中的数据
def register ( ) :
print ( '注册' )
def login ( ) :
print ( '登入' )
dic = { '1' : register, '2' : login}
while True :
print ( '
1. 注册
2. 登入
')
choice = input ( '请选择您的功能编号>>>:' ) . strip( )
if choice not in dic:
print ( '功能编号不存在' )
dic. get( choice) ( )
闭包函数
1. 定义在函数内部的函数
2. 用到了外部函数名称空间中的名字
实际是另外一种传参方式
传参方式一:
要什么传什么
def func ( name, age) :
print ( name, age)
传参方式二:
闭包函数
def index ( name, age) :
def inner ( ) :
print ( name, age)
return inner
res = index( 'jason' , 18 )
res( )
装饰器
import time
def index ( ) :
time. sleep( 3 )
print ( 'from index' )
1. 在调用idex函数的前后添加代码
start_time = time. time
index( )
end_time = time. time
print ( 执行的时间是:end_time - start_tiem)
2. 就只能调index 如果执行的地方多呢
def get_time ( xxx) :
start_time = time. time
xxx( )
end_time = time. time
print ( 执行时间是:end_time - start_time)
get_time( index)
3. 可又不符合装饰器的特征 试试第二种传参
def outer ( xxx) :
def get_time ( ) :
start_time = time. time
xxx( )
end_time = time. time
print ( 执行时间是:end_time - start_time)
return get_time
res = outer( index) 函数名可以当做变量名
index = outer( index)
index( )
4. 可如果要尽心传参呢
def index ( name) :
time. sleep( 3 )
print ( 'from index' , name)
def outer ( xxx) :
def get_time ( * args, ** kwargs) :
start_time = time. time
xxx( * args, ** kwargs)
end_time = time. time
print ( 执行时间是:end_time - start_time)
return get_time
res = outer( index) 函数名可以当做变量名
index = outer( index)
index( 'jason' )
5. 如果被装饰对象有返回值呢
def index ( name) :
time. sleep( 3 )
print ( 'from index' , name)
return 'haha'
def outer ( xxx) :
def get_time ( * args, ** kwargs) :
start_time = time. time
rea = xxx( * args, ** kwargs)
end_time = time. time
print ( 执行时间是:end_time - start_time)
return res
return get_time
res = outer( index) 函数名可以当做变量名
index = outer( index)
index( 'jason' )
def outer ( func) :
def inner ( * args, kwargs) :
在被装饰对象执行前做的操作
res = func( * args, ** kwargs)
在被装饰对象执行之后做的操作
return res
return inner
如果有多层语法糖的话 它的加载顺序是由下而上
有参装饰器
def login_auth ( mode) :
def outer ( func) :
def inner ( * args, ** kwargs) :
res = func( * args, ** kwargs)
return res
return inner
return outer
@login ( 'file' ) 函数名加括号执行优先级别最高 先看函数名加括号 再是语法糖操作
def index ( ) :
print ( 'index' )
递归函数
最大递归深度为1000 左右
l1 = [ 1 , [ 2 , [ 3 , [ 4 , [ 5 , [ 6 , [ 7 , [ 8 , ] ] ] ] ] ] ] ]
def func ( l1) :
for i in l1:
if instance( i, int ) :
print ( i)
else :
func( i)
func( l1)
算法之二分法
l1 = [ 784 , 566 , 452 , 342 , 243 , 109 , 97 , 89 , 74 , 34 , 21 , 15 , 9 , 3 , 0 ]
def get_num ( l1, target) :
if len ( l1) == 0 :
print ( '找不到' )
return
middle = len ( l1) // 2
if l1[ middle] > target:
left = l1[ middle+ 1 : ]
get_num( left, target)
elif l1[ middle] < target:
right = l1[ : middle]
get_num( right, target)
else :
print ( '找到了' )
get_num( l1, 3 )
三元表达式
数据值1 if 条件 else 数据值2
条件成立则使用数据值1 条件不成立则使用数据值2
当结果是二选一的情况下 使用三元表达式更为简便
多种生成式
列表生成式:
l1 = [ 'jason' , 'kevin' , 'tony' , 'oscar' ]
res = [ f' { i} _NB' for i in l1]
print ( res) [ 'jason_NB' , 'kevin_NB' , 'tony_NB' , 'oscar_NB' ]
字典生成式:
res = { j: i for i, j in enumrate( l1) }
print ( res)
集合生成式:
res = { i for i in l1}
常见内置函数
map ( ) 映射
zip ( ) 拉链
filter ( ) 过滤
max ( ) 最大 min ( ) 最小
ruduce( ) 传入多个值 返回一个值 与模块from functools import reduce
isinstance ( ) 传入两个值 一个是数据值 一个是数据类型 再判断给数据值是否属于该类型
sum ( ) 求和
enumerate 枚举
pow ( ) 次方
round ( ) 四舍五入
divmod ( ) 传入两个值 第一个数据值除以第二个数据值 返回的是元组的形式整除数和余数
可迭代对象
就是内置含有双下iter 方法的都称为可迭代对象
可迭代对象:能够被for 循环的都称为可迭代对象
迭代器对象
是由可迭代对象调用_iter_方法产生的
迭代器对象判断的本质是是否内置有_iter_和_next_方法
提供了一种不依赖于索引取值的方式 也正因为有迭代器的存在字典和集合才能够被for 循环
for循环本质
先将in 后面的数据调用_iter_方法转变成可迭代对象
依次让迭代器对象调用_next_取值直到取不到值 for 循环会自动捕获异常并处理
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!