函数--推导式
收录于话题
#Python入门
27个

概要:
1.列表推导式:[结果 for 循环 if 筛选]
2.字典推导式:{key:value for 循环 if筛选}
3.集合推导式:{key for 循环 if 筛选}
4.生成器推到式:(结果 for 变量 in 可迭代对象 if 条件筛选)
1.列表推导式 [结果 for循环 if筛选]
例子1:
lst = ["python%s" % i for i in range(1, 17)]
print(lst) #结果为['python1', 'python2', 'python3', 'python4', 'python5', 'python6', 'python7', 'python8', 'python9', 'python10', 'python11', 'python12', 'python13', 'python14', 'python15', 'python16']
例子2: # 100以内能被3整除的数的平方⽅
lst = [i*i for i in range(1, 101) if i % 3 == 0]
print(lst)
例子3:寻找名字中带有两个e的名字
names = [['Tom', 'Billy', 'Jefferson', 'Andrew', 'Wesley','Steven','Joe'],
['Alice', 'Jill', 'Ana', 'Wendy', 'Jennifer', 'Sherry','Eva']]
lst = [name for first in names for name in first ifname.count("e") = 2 ]
print(lst)
例子4:求(x,y)其中x是0-5之间的偶数,y是0-5之间的奇数组成的元祖列表
lst=[(x,y)for x in range(6) for y in range(6) if x%2==0 and y%2==1]
print(lst)
例子5:删除姓张的人
一种:
lst = ["张无忌","胡辣汤","张三丰","赵铁柱","牛栏山"]
lst1=[i for i in lst if not i.startswith("张")]
print(lst1)
二种:filter
print(list(filter(lambda x :not x.startswith("张"),lst)))
2.字典推导式, {key: value for循环 if 筛选}
例子6: key 和value调换
dic = {"张无忌":"九阳神功", "乔峰":"降龙十八掌", "楚留香":"帅"}
d = {dic[k]: k for k in dic}
print(d) key 和value调换
例子7:两个列表组成字典
lst1 = ["东北", "陕西", "山西", "开封", "杭州", "广东", "济南"]
lst2 = ['大拉皮', "油泼面", "老陈醋", "灌汤包", "西湖鲤鱼","早茶", "胶东一锅鲜"]
dic = {lst1[i]:lst2[i] for i in range(len(lst1))}
print(dic)
3.集合推导式, {key for循环 if 筛选}作用是去重
例子8:
lst = ["周杰伦","周伯通","周润发","周伯通","周笔畅","周伯通","周星驰","周伯通"]
s = {el for el in lst}
print(s) #{'周杰伦', '周伯通', '周润发', '周星驰', '周笔畅'}
例子9:
lst = [1,-1,6,-6,123,3245,-9,0,9]
s={abs(i) for i in lst}
print(s) #{0, 1, 6, 9, 3245, 123}
4.元祖无推导式,因为其不可变.
5.生成器推到式:(结果 for 变量 in 可迭代对象 if 条件筛选)
深坑==>生成器. 要值得时候才拿值.
生成器的表达式和列表的表达式很像
1).生成器表达式和列表推导式的区别:
1. 列表推导式比较耗内存,.一次性加载;生成器表达式几乎不占用内存. 使用的时候才分配和使用内存
2.得到的值不一样. 列表推导式得到的是一个列表,.生成器表达式获取的是一个生成器.
举个例子. 同样一篮子鸡蛋. 列表推导式: 直接拿到一篮子鸡蛋.生成器表达式: 拿到一个老母鸡. 需要鸡蛋就给你下鸡蛋
生成器的惰性机制: 生成器只有在访问的时候才取值,说白了你找他要他才给你值.不找他要他是不会执行的.
2).生成器的特点:
1. 节省内存
2. 惰性机制(只有执行__next__()才会取值)
3. 只能向前. 不能反复
例子10:
gen = (i for i in range(10)) #创建一个生成器
print(gen) #<generator object <genexpr> at 0x0000000001E36830> 不是执行
print(gen.__next__()) #这是执行0
print(gen.__next__()) #1
例子11:面试题
def func():
print(111)
yield 222
g = func() # 生成器g
g1 = (i for i in g) # ⽣生成器g1. 但是g1的数据来源于g
g2 = (i for i in g1) # 生成器g2. 但是g2的数据来源于g1
print(list(g1)) # 获取g1中的数据.g1数据来源于g,此时结果为111 [222]
print(list(g2)) #获取g2中的数据,最终来源于g,已经取完了因此[]
print(list(g))#[]
最终结果为 111 [222] [] []
例子12:也是一个面试题
先搞清一个概念
def test():
for r_i in range(4):
yield r_i
g = test()#创建g生成器
ge =(i for i in g) #不要以为for循环g代表执行了生成器的内容,单独把for i in g 拿出来的话才是执行生成器。此刻只是单纯的创建生成器ge。
print(list(ge)) #[0, 1, 2, 3]
print(ge)#<generator object <genexpr> at 0x0000000001E16938>
接下来看题:
def add(a, b):
return a + b
def test():
for r_i in range(4):
yield r_i
g = test() # 惰性机制 # 创建生成器,不执行,
for n in [2, 10]:
g = (add(n, i) for i in g) #生成器表达式,此时也不执行
#相当于n =2 时 ,g =(add(n, i) for i in g)
#n =10 时,g=(add(n, i) for i in g)
#此时g生成器没执行所以g=(add(n, i) for i in (add(n, i) for i in g))此时n=10
print(list(g))
#接下来取值,g的值为0,1,2,3,此时n为10,2不起作用,所以最终的结果为
[20,21,22,23]
















