列表生成式,生产器
#列表生成式,可以是代码更复杂a = [i for i in range(10)] #这里的i,可以使用函数来装饰print(a)#生产器:就是数据在调用的时候才有b = (x*2 for x in range(1000))#print(b[3]),直接调用会报错,因为数据还没有生产呢b.__next__()b.__next__()b.__next__()# print(b[1]),这也会报错,因为生成器只保持当前数据print(b.__next__())#只能使用这样的方式取值print((x*2 for x in range(10)))#将一个函数编程一个生成器#斐波那契数列def feibo(max): n,a,b = 0 ,0,1 while n < max : # print(b) yield b #这样就样这个函数变成一个生成器了,生成器只有__next__()方法 a,b = b,a+b #这里的意思是,将b赋值给a,将 a+b的结果赋值给b(这里的a不是赋值后的a) #这句话的意思就是 t = tuple(b,a+b) n = n+1 return "done"# feibo(6)f = feibo(6)#这样就将 函数给挂起了,运行其他的逻辑,然后在返回,当取到最后一个在next就会报错,可以使用try except 来处理异常try: while True: f.__next__()except StopIteration as e:#将最后的返回值复制个e的这个异常对象中 print(e.value)#简单的一个生产消费者模型def consume(name): print("%s is begin"%name) while True: a = yield print("%s 开始消费 %s"%(name,a))def provide(): #这里有两个消费者 c1 = consume("zhang") c2 = consume("yu") c1.__next__() c2.__next__() for i in range(10): c1.send(i)#这就是讲i传给上面yield这个地方 c2.send(i)provide()#什么是迭代器,被next方法的迭代对象就是迭代器,其中list,set都是可迭代对象,但是不是迭代器#可以直接做用于 for循环的对象,就是迭代对象 可以使用from collections import Iterable#Iterator迭代器from collections import Iteratorisinstance("abc",Iterable)
匿名函数,内置函数
#1.匿名函数,就是没有方法名的函数,使用 lamdba 关键字a = lambda x:x+2# lambda x:x+2 这就是一个匿名函数,x代表参数,x+2代表 函数体print(a(3))#2.内置函数#1.abs()求绝对值print(abs(-3.5))all()#迭代器中所有的元素都为真,才是真any()#迭代器中任何一个为真就是真ascii()#将数字转为ascii对象的值bin()#转为二进制bool()#测试一个对象是正还是假bytearray()#字节数组callable()#是否可以调用chr(),ord()#查看10进制对象的ascii/查看ascii对应的十进制dir()#返回当前范围内的变量globals(),locals()#全局属性,局部属性zip()#将两个列表,1,1对应转为一个新的列表b= zip([1,2,3],["a","b","c"])for i in b: print(i)from functools import reducea = reduce(lambda x,y:x+y,range(10))print(a,type(a))#过滤器,按照fun,条件进行过滤,这里可以直接使用匿名函数来简化代码c = filter(lambda x:x<5, [i for i in range(10)])for i in c: print(i)d = map(lambda x:x*2,[i for i in range(10)])for i in d: print(i)#讲map与reduce结合使用,求 1!+2!+3!+4!#阶乘,这个是4的阶乘factorial = reduce(lambda f,c:f+c,map(lambda a:reduce(lambda x,y:x*y,range(1,a+1)),range(1,5)))print(factorial,type(factorial))#排序#将字典排序info = {1:"a",5:"f",3:"c",2:"b",4:"d"}#1.按key进行排序print(sorted(info.items()))#2.如果按value排序呢print(sorted(info.items(),key = lambda x:x[1]))
装饰器:
#1.高阶函数,参数是函数,或者返回值是函数的#嵌套函数,就是函数里面在定义函数#可以讲函数,当成一个变量进行传递#高阶函数+嵌套函数==装饰器#装饰器的作用就是,不改变原函数,不改变函数的调用方式import time,pickle#1.高阶函数 将函数作为参数传递def deco1(func):#将函数当成一个变量传递过来,实际上是将函数的内存地址传递过来,函数名+()调用这个函数 start_time = time.time() func() end_time = time.time() print("%s这个函数运行是时间%d"%(func,end_time-start_time))#deco1(func)#2.高阶函数 返回值为函数def deco2(func): start_time = time.time() #这句话的意思就是将func这个函数的内存地址返回去 return func end_time = time.time() print("%s这个函数运行是时间%d" % (func, end_time - start_time))# func = deco2(func)# func()#3.嵌套函数,就是在函数里面定义函数def deco3(): def deco4(): print("deco4..run") #函数就相当于一个变量,定义一个函数,就相当于在内存空间声明了一个内存地址 #所以这个地方一定要调用,要不只是声明没有调用的地方 deco4()# deco3()#如何对一个函数进行装饰,并且不改变函数的调用方式#例如对func()进行装饰#1.不改变函数的内部def deco5(func): start_time = time.time() func() end_time = time.time() print("%s这个函数运行是时间%d" % (func, end_time - start_time))#2.不改变函数的调用方式,(使用嵌套函数,再包一层,将包装后的函数返回)def deco6(func): def waps(): start_time = time.time() func() end_time = time.time() print("%s这个函数运行是时间%d" % (func, end_time - start_time)) return waps@deco6def func(): time.sleep(1) print("func运行")#这个是调用:这样就实现的装饰# func = deco6(func)#这句话,python直接使用 @装饰器名称表示# func()#如果函数带有参数怎么处理呢,就是在内部函数带参数来接受被装饰函数的参数def deco7(func): def wrapper(name): start_time = time.time() func(name) end_time = time.time() print("%s这个函数%s运行是时间%d" % (func, name,end_time - start_time)) return wrapper@deco7def func1(name): print("name",name)func1("aa")#如果func1有多个参数呢,所以使用可变参数来接受,最后修改为def deco8(func): def wrapper(*args,**kwargs): start_time = time.time() func(*args,**kwargs) end_time = time.time() print("%s这个函数运行是时间%d" % (func, end_time - start_time)) return wrapper@deco8def func2(name,age): time.sleep(1)# func2("zhang",22)#如果装饰器自己也需要参数,改如何处理呢#例如#home 和 account 这两个函数使用不同的登陆方式登陆的,如何使用一个装饰器满足所有需求#这里使用了同一张验证方式,如果装饰器上传一个参数,代表这个方法不需要登陆该如何处理def login(fun): def wrapper(*args,**kwargs): name = input("your namne") passwd = input("your password") if name == "zhang" and passwd == "123": fun(*args,**kwargs) else: print("登陆失败") return wrapperdef loginArg(type): def login(fun): def wrapper(*args,**kwargs): if type == "login" : name = input("your namne") passwd = input("your password") if name == "zhang" and passwd == "123": fun(*args,**kwargs) else: print("登陆失败") elif type == "nologin" : fun(*args, **kwargs) return wrapper return login@loginArg(type="login")def home(name): print("%s in home"%name)#这个就不需要登陆@loginArg(type="nologin")def account(name): print("%s in account"%name)
json序列化和pickle序列化
#序列化和反序列化json,pickleimport json#json的load 与dump是保存和加载 json格式的文件info = { "name":"zhang","age":22,"addr":"china"}info1 = [1,2,3,4,5,6,login]#这种info1中保存了一个函数的内存地址# print(info1)with open("json","w") as f: # json.dump(info1,f) f.writelines(json.dumps(info))#或者使用 # f.writelines(json.dumps(info1)) #这样在使用json就会报错,因为 function' is not JSON serializablewith open("json","r") as f: # json.loads() # aa = json.load(f) #可以写成 aa = json.loads(f.read()) print(type(aa))#可以看到,这样的aa的类型是 dict,如果是一帮的#json是所有语言都有的共性的#这里就使用pickle这个序列化,是python特有的个性的序列化with open("pickle","wb") as f: pickle.dump(info1,f) #write() argument must be str, not bytes #这句话明显表示,pickle.dump(info1,f)这需要一个(所以,这里将文件的打开方式按照b形式打开) #或者写成 # f.write(pickle.dumps(info1))with open("pickle","rb") as f: # aa = pickle.load(f) aa = pickle.loads(f.read()) print(type(aa),aa)#这样就可以取出来了,但是这里有一个问题,因为列表中有一个函数,如果在另一个文件打开的话,这个函数会报错,所以需要对这个函数特殊处理