?判断与循环
? ? ?判断语言if/elif/else
if语句
它包含了几个部分:
1.if关键字,表示这是一条判断语句
2.<condition>表示判断条件,当个条件满足时,执行<statements>中的代码,若条件不满足,则代码不会执行。
3.冒号表示代码块的开始
4.<statements>表示条件满足时,执行代码块
语法:
?if?条件:
?????代码块
注意:
1.冒号必须是英文状态下
?2.必须要缩进
执行流程图
?代码
1.把字符串转换成int类型
a?=?eval("10")
???print(a)?#10
???print(type(a))?#<class?'int'>
2.对字符串进行计算
?a?=?"3*2"?
???print(a)?#3*2
???b?=?eval(a)
???print(b)?#6
#input("请猜一个数字")?---Str
#eval()?把Str转换成int
guess??=?eval(input("请猜一个数字"))
if?guess?==99:
????print("恭喜你猜对了")?#恭喜你猜对了
二分支
语法
if?条件:
?????代码块
?else:
?????代码块
执行流程图
guess??=?eval(input("请猜一个数字"))
if?guess?==?99:
????print("恭喜你猜对了")
else:
????print("谢谢惠顾")
多分支
语法
if?条件:
?????代码块
?elif?条件:
?????代码块
?elif?条件:
?????代码块
else:
??????代码块
执行流程图
score?=?eval(input("请输入一个成绩:"))
if?score?>=?90:
????print("a")
elif?90?>?score>=80:
????print("B")
elif?80?>score>=70:
????print("C")
elif?70>score>=60:
????print("D")
else:
????print("不及格")
三目运算符
语法
满足条件的代码块??if?条件?else?不满足条件的代码块
执行流程
?语法:
???if的缩写
满足条件的代码块??if?条件?else?不满足条件的代码块
guess??=?eval(input("请猜一个数字"))
print("恭喜你,猜对了")if?guess?==?99?else?print("谢谢惠顾")
在python中,大部分的值被当作真,出以下几种情况:
1.False,包括所有计算机结果为false的表达式
2.None,包括所有计算机结果为None的表达式
3.整数0值,包括所有计算机结果为0的表达式
4.空字符串,空列表,空字典,空集合,空元组
循环语句for
循环结构主要有两种:
1.while循环
2.for循环
语法
for?变量?in?遍历结构:
? 代码块
执行流程
?
用法
1.字符串遍历
Str?=?"hello?python"
for??i?in?Str:
????print(i)
2.列表遍历
list01?=?["赵丽颖","舒畅","戚薇","朱梓骁"]
for?i?in?list01:
????print(i)
3.字典遍历
dict01?=?{"天龙八部":"段誉","倚天屠龙记":"张无忌","九阴真经":"周芷若","射雕英雄传":"郭靖"}
1.用普通遍历,只能打印key
for?i?in?dict01:
????print(i)
?2.字典.items()??返回一个元组
for?t?in?dict01.items():
????print(t)
????print(type(t))
3.获取单独的key和value,就是想办法把元组拆分,返回基本数据类型
?????把元组赋值给两个变量
?<class?'str'>
??<class?'str'>
for?k,v?in?dict01.items():
????print(k)
????print(type(k))?#Str
????print(v)
????print(type(v))?#Str
Set集合遍历
set01?=?{1,2,3,4}
for?i?in?set01:
????print(i
无限循环(while)
语法
?while?条件:
?????变量改变公式
?????代码块
a?=?10
while?a>0:
?#变量不断改变,为了满足条件,避免进入死循环
?a?-=?1
????print(a)
range()函数可以生成一个连续的证书列表,则基本用法:
1.range(stop):生成从0开始到stop-1的整数组成的列表
2.range(start,stop):生成从start开始到stop-1的整数组成的列表
3.range(start,stop step):生成从start开始到stop-1,间隔为step的整数组成的列表
for i in range(5):
print(i)
for i in range(1,5):
print(i)
for i in range(1,5,2):
print(i)
break 和continue的运用
break跳出并结束当前整个循环,不执行循环后的语句
continue结束当次循环,继续执行后续次数循环
?
for?i?in?[1,2,3,4,5]:
????if?i==2:
????????break
????print(i)?#1
for?i?in?[1,2,3,4,5]:
????if?i==2:
????????continue
????print(i)?#1
循环加else
语法
for??变量?in?遍历结构:
??????代码块
??else:
??????代码块
执行流程
?1.先执行完for循环
?2.执行完以后执行else
for?i?in?[1,2,3,4,5]:
????print(i)
else:
????print("循环结束")
??
同理,while能不能加else,可以,和上面一样
while语法
while?<条件>?:?
????<语句块1>
else?:?
????<语句块2>
#循环结束后,会执行else的代码
推导式
1.列表推导式
list01?=?[1,2,3,4]
a=??[i+1?for?i?in?list01]
print(a)?#[2,?3,?4,?5]
print(type(a))?#<class?'list'>
2.字典推导式
dict01?=?{"王五":20,"张三":50,"李四":80,"赵六":18}
for?k,v?in?dict01.items():
????print(k,v)
{print(k,v)?for?k,v?in?dict01.items()}
3.集合推导式
list01?=?[1,2,3,4]
a=??{i+1?for?i?in?list01}
print(a)?#{2,?3,?4,?5}
print(type(a))?#<class?'set'>
4.元组类型
#把里面的代码看成一个整体,一个对象
#利用我们的tuple()函数
list01?=?[1,2,3,4]
a=??tuple(i+1?for?i?in?list01)
print(a)??#(2,?3,?4,?5)
print(type(a))?#<class?'tuple'>
? ?#把3+2变成一个整体
? (3+2)/9
4..3函数进阶
4.3.1? ?函数参数传递
1.参数的传递参数
在python中,函数参数传递机制与赋制机制一样,本质都是共用内存地址,不会真正的复制对象,这种共享内存的方式叫作引用机制?。
a传进来的时候传进来的是内存地址
?可以理解是??x=?a
def?isid(x):
??#打印参数的内存地址
print(id(x))
a?=?10
#变量的内存地址
print(id(a))?#140731588047408
#a变成的参数,打印参数内存地址
isid(a)?#140731588047408
2.默认参数的传递
在默认参数的情况下,python会定义函数时,预先为默认参数分配内存,每次调用默认参数,python会从这个预先分配好的内存地址得到这个默认参数,以免每次生成一个额外的默认参数,这种情况可能会出现一些与直觉不符的结果。
#定义一个带有默认参数的函数
def?add(x,y=10):
????sum01?=?x+y
????return?sum01
1.add(2)??x=2??y=10
2.add(2,3)??x=2??y=3
print(add(2))?#12
print(add(2,3))?#5
能不能传参传入一个序列类型,比如list,让他默认是[]
def?add(list01?=?[]):
????list01.append(1)
????return?list01
#第一调用
print(add())?#[1]
#第二次调用
print(add())?#[1,?1]
#第三次调用?
print(add())?#[1,?1,?1]
?不定数目的参数
一个?*
一个*?:代表的是可变参数(就是可以是多个值)
def?add(x,*y):
????sum01?=?x
????for?i?in?y:
????????sum01?+=?i
????return?sum01
print(add(1,2,3,4,5))?#15
两个*
**y代表可以使用任意??键值(字典)??作为参数
?**y就相当于字典类型
def?func_add(x,**y):
????sum01?=?x
#切记这里是字典的循环
??for?k,v?in?y.items():
????????print(k,v)
????#把v(值)进行和x相加
?????sum01?+=?v
????return?sum01
调用
a=3,b=4,c=5?---->?{"a":3,"b":4,"c":5}
print(func_add(1,a=3,b=4,c=5))?#13
name
1.执行本文件的时候,name==main
#打印name这个属性
#执行本文件的时候,打印的是main,__name__?==?__main__
print("1、"+__name__)?#1、__main__
2.在被import导入到别的文件的时候,name==文件名字
语法:
?一个文件就是一个模块,导入模块,就相当于导入文件,可以直接写
????import??文件名字
import?本文件?as?bwj
#在其他类中运行导入的文件名字,__name__==文件名字
print(bwj.__name__)?#本文件
高阶函数
含义:高阶函数是一个(?以函数为参数,或者以函数为返回值的)函数
问题:函数可以是参数,参数是变量,那么函数可以是变量吗?
参数其实就是变量进行了赋值,函数能不能是变量
函数为变量(补充)
??函数为变量并不是高阶函数
1.函数的对象性
?对象性意味可以对函数进行一下操作:
1.将函数作为一个参数传递给另一个函数
2.将函数作为字典的值
3.将函数作为另一个函数的返回值
常用的高阶函数
2.以函数为参数的函数
def apply_func(f,sq):
return [f(x) for x in sq]
3.以函数为返回值的函数
函数的返回值也可以是一个函数
def pow_func(f,sq):
def func(x)
return x** num
return func
#定义一个函数,传入一个参数,求这个参数的平方
def?func_pf(x):
????return?pow(x,2)
#字典
#已知李四的年龄是5的平方,求李四的年龄
dict01?=?{"张三":20,"李四":func_pf}
?调用
??1.func_pf?=?dict01["李四"]??根据key获取value,vaule是一个函数对象
??2.age02?=?func_pf(5)?#调用函数就能获取年龄
#字典的特点是根据key获取value
age01?=?dict01["张三"]
print(age01)?#20
#顾名思义,通过李四,我们可以拿到函数func_pf
#拿到的是函数对象,我们不能直接打印
func_pf?=?dict01["李四"]
print(func_pf)?#<function?func_pf?at?0x000001E25A23D048>
age02?=?func_pf(5)
print(age02)?#25
?函数为参数 ? 1.#普通函数
def?func_pf(x):
????return?x**2
2.高阶函数,以函数为参数
def?func_add(func_pf):
?return?func_pf+10
a?=?func_add(func_pf(2))
print(a)?#14
map()
?map(fun,x)?转换,接受一个序列,按照fun的函数逻辑转换成新的序列,返回一个map对象
-
x必须是一个序列 -
返回一个map对象
执行流程
?map(fun,x)?转换,接受一个序列,按照fun的函数逻辑转换成新的序列,返回一个map对象
?1.?x必须是一个序列
?2.返回一个map对象
def?func_add(x):
????return?x+1
??把原来的数据,经过func_add函数以后,每一个都加1,然后输出新的列表
m?=?map(func_add,[1,2,3,4,5])
print(m)?#<map?object?at?0x00000248E965C788>
print(list(m))?#[2,?3,?4,?5,?6]
filter()
filter(func,x)?过滤,接受一个序列x,按照func函数要求进行转换,?
????func函数返回?True?或?False,最后将返回?True?的元素放到新列表中。
????返回filter对象
filter(func,x)?过滤,接受一个序列x,按照func函数要求进行转换,?
????func函数返回?True?或?False,最后将返回?True?的元素放到新列表中。
????返回filter对象
def?func_ifScore(x):
?return??x>=60
f?=??filter(func_ifScore,[80,98,70,34,60,59,10])
print(f)??#<filter?object?at?0x00000232CC78C808>
print(list(f))?#[80,?98,?70,?60]
#比较运算符,本身就是返回布尔值的
????#如果大于等于60就是Ture,否则就是False
reduce()函数
from?functools?import?reduce
?reduce(func,x)?计算,接受一个序列,把列表中的每一个值按照函数进行累加或者别的运算
???返回一个计算数值
???1.因为是计算,所以我们的func是两个参数
???2.必须要导包
#累加???1+2+3+4+5
def?func_add(x,y):
????return?x+y
a?=?reduce(func_add,[1,2,3,4,5])
print(a)?#15
zip()
zip(list01,list02)?拉链、压缩
??用于将可迭代的对象作为参数,将对象中对应的元素打包成一个个元组,返回一个对象
??1.参数必须是可迭代的序列类型
??2.对象里面放的是一个一个的元组
??3.返回一个zip对象
ist01?=?[1,3,5,7,9]
list02?=?[2,4,6,8,10]
z?=?zip(list01,list02)
print(z)?#<zip?object?at?0x00000292EE17C7C8>
#print(list(z))?#[(1,?2),?(3,?4),?(5,?6),?(7,?8),?(9,?10)]
问题:?数据不一样多了,拉链不一样长了,结果该怎么办呢
?以短的为基础
list03?=?[1,3,5,7,9,11,13]
list04?=?[2,4,6]
a?=?zip(list03,list04)
#print(list(a))?#[(1,?2),?(3,?4),?(5,?6)]
?a是一个压缩、拉链数据,能不能解压呢,
?1.符号是*
?2.zip(*list类型)
?3.声明两个变量去承接
?4.zip对象如果执行过了,就不存在了
b?=?list(a)
list05,list06?=?zip(*b)
print(list05)?#(1,?3,?5)
print(list06)?#(2,?4,?6)
sorted()
sorted(序列类型的对象,key=函数,reverse=True/False)??排序
??1.reverse=True/False???升序是False?降序是Ture
#list里面可以放任何数据类型
list01?=?[{"name":"张三","age":20},
?????????{"name":"李四","age":30},
?????????{"name":"王五","age":18},
?????????{"name":"小明","age":8}
????????]
def?func_age(list01):
?age01?=?list01["age"]
????return?age01
s?=?sorted(list01,key=func_age,reverse=False)
print(s)
函数为返回值
语法
?def?func_name01(参数1):
???????def?func_name02(参数2):
???????return?逻辑
???????return?fun_name02
#x的y次方
def?func01(x,y):
????return?x**y
?简化1
???以函数为返回值进行简化
???1.闭包。函数里面的子函数,叫做闭包
lambda表达式
含义:lambda表达式是一行函数。在其他语言中叫做匿名函数
lambda表达式:一行函数
def?func01(x,y):
????return?x**y
lambda?x,y:x**y
函数的递归
含义:
?递归是指函数在执行过程中调用了本身。简单来说就是自己调用了自己
?1.自己调用自己
?2.一定要有一个条件,进行退出调用
阶乘:
??比如说给一个数据5,阶乘5*4*3*2*1
??n?=?5*(5-1)
??n?=n*(4-1)
??n?=n*(3-1)?
??n?=n*(2-1)
????总结规律
?n!?=?n*(n-1)
def?func_jc(n):
??if?n==1:
????return?1
??else:
????return?n*func_jc(n-1)
print(func_jc(5))?#120
非递归
?#下标是从0开始的
def?func(n):
????#初始化两个变量
????a,b=1,1
????#range(5)?---->0,1,2,3,4
????for?i?in?range(n):
????????a,b=b,a+b
????return?a
print(func(5))?#8
迭代器
含义:
?迭代器是一个可以遍历容器的一个对象
-
迭代器返回一个对象 -
那些东西可以进行迭代
??容器类型的---list??set??字典?字符串
方法
?迭代器
??#注意是两个下划线
??list01.__iter__()?返回一个迭代器对象
?????<list_iterator?object?at?0x0000024037E0C588>
list01?=?[1,2,3,4]
#注意是两个下划线
a?=??list01.__iter__()
print(a)?#<list_iterator?object?at?0x0000024037E0C588>
问题:
1.我听要他何用,他是一个对象,我想要的是值
?迭代器对象.__next__()?返回一个值
?2.他只能返回第一个值吗??no
??因为next()可以记忆位置,每次你调用一次,他会记住这位置,然后下一次从下一个位置开始
??3.我要是一直调用,可以吗
????报错StopIteration,没有数据了
????我们的next没有办法回头,不会从头开始,他只会从记忆的位置的开始
print(a.__next__())?#1
print(a.__next__())?#2
print(a.__next__())?#3
print(a.__next__())?#4
print(a.__next__())?#报错
迭代
list01?=?[1,2,3,4]
#注意是两个下划线
a?=??list01.__iter__()
迭代对象的遍历
?1.__next__()?不会从头开始,?每次从记忆的位置开始
?2.for循环就相当于是不断的打印__next__()。但是为什么没报错
???自己抛出StopIteration,然后停止循环
生成器
含义:生成器也是一种迭代器,但是你只能对其迭代一次。
生成器跟普通函数不同的是,生成器是一个返回迭代器的函数,只能用于迭代操作,更简单点理解生成器就是一个特殊的迭代器。
生成器可以一边循环一边计算
优点:是节省内存
关键字是:yield
语法:
def?func_name(canshu):
????for?i?in?canshu:
????????yield?luoji
总结
-
生成器都是迭代器,迭代器不一定是生成器 -
字符串,列表,元组,字典,集合都可以被for循环,说明他们都是可迭代对象 -
迭代器的两个方法:1.有__iter__()?2.?有__next__() -
isinstance()?类型判断。isinstance(a,Iterable)?判断a?是否是可迭代对象。
装饰器
含义:
1.装饰器是一个函数
?2.装饰器是一个?为函数添加新的属性??的函数
?3.通过闭包对函数添加新的属性
语法
?1.def?func_a()??#带有新特新的闭包函数
???@def?func_a
?2.def?func_b()??#被修饰的函数
相当于func_a(func_b)
?1.装饰器是一个函数
?2.装饰器是一个?为函数添加新的属性??的函数
?3.通过闭包对函数添加新的属性
闭包函数:函数的子函数就是闭包函数
变量作用域
变量作用域:是指变量的有效生存空间
1.函数局部作用域? L(local)?局部作用域?
2.闭包作用域??E(Enclosing)?闭包函数中的作用域
3.全局作用域? G(Global)?全局作用域
4.内置作用域??B(Built-in)?内置作用域
如果有重名的变量,局部优先于闭包,闭包优先于全局,全局优先于内置
作用域是按照变量的查找顺序?L>E>G>B
L(local)?局部作用域
def?func():
??????#a是函数中的变量,是局部变量,只能在函数中使用
??????a=10
??????print(a)
#a是不存在的
print(a)
E(Enclosing)?闭包函数中的作用域
??nonlocal??:把闭包外的变量引用过来
#刚出生的年龄,是全局变量,意味这谁都是从这个年龄开始的
age?=?1
def?qunian():
??????#闭包外的变量,局部变量??4-11能用
??????age?=?19
??????def?jinian():
G(Global)?全局作用域
global??把全局的age引用过来
age?=?20
def?func():
??????#把全局的age引用过来
??????global?age
??????#局部
??????#前面的a相当于是重新赋值的a,是局部的
??????#后面的a是要进行相加的数据,所以要有这个数据,所以是全局的
??????age=1?+?age
??????return?age
??????
print(func())?#30
B(Built-in)?内置作用域
系统固定模块里面的变量,比如?int,?bytearray?等。
比如函数名?abs、char?和异常名称?BaseException、Exception?等等。
异常
语法
Try?–?except-else
?try?-except-else
?try:
??????代码块
?except?<错误的名字(可写可不写)>:
???????代码块
?...........
?else:
???????代码块去??
可以把else去掉
try:
??????代码块
?except?<错误的名字(可写可不写)>:
???????代码块
注意:1.try不能单独使用
?????2.错误的名字(可写可不写)
运行结果:
???报错(除数是0),运行的是except
???不报错(除数不是0),运行的是else
运行结果:
???报错(除数是0),运行的是except
???不报错(除数不是0),运行的是else
try:
??????s?=?eval(input("请输入一个数字:"))
??????a?=?10/s
except?ZeroDivisionError:
??????print("除数不能是零")
else:
??????print("除数是正常的,运行成功")
Raise关键字
?语法:
?raise:无论代码是否异常,他自己会触发异常
语法:
?raise?异常名称
try:
??????s?=?eval(input("请输入一个除数:"))
??????a?=?10/s
??????#无论你的除数等不等于0,他都会报错
??????raise?ZeroDivisionError
except?ZeroDivisionError:
??????#except是异常的时候给出的警告
??????print("警告:除数不能为0")
注意:
请输入一个除数:3
警告:除数不能为0
常见的异常列表(要求再认)
BaseException | 所有异常的基类 | SystemExit | 解释器请求退出 | KeyboardInterrupt | 用户中断执行(通常是输入^C) | Exception | 常规错误的基类 | StopIteration | 迭代器没有更多的值 | GeneratorExit | 生成器(generator)发生异常来通知退出 | StandardError | 所有的内建标准异常的基类 | ArithmeticError | 所有数值计算错误的基类 | FloatingPointError | 浮点计算错误 | ValueError | 传入无效的参数 | ZeroDivisionError | 除(或取模)零?(所有数据类型) | KeyError | 映射中没有这个键 | AttributeError | 对象没有这个属性 |
|