一,函数的分类
#1、内置函数
为了方便我们的开发,针对一些简单的功能,python解释器已经为我们定义好了的函数即内置函数。对于内置函数,我们可以拿来就用而无需事先定义,如len(),sum(),max()
#2、自定义函数
很明显内置函数所能提供的功能是有限的,这就需要我们自己根据需求,事先定制好我们自己的函数来实现某种功能,以后,在遇到应用场景时,调用自定义的函数即可。
二,定义函数
#语法
def 函数名(参数1,参数2,参数3,...):
'''注释'''
函数体
return 返回的值
#函数名要能反映其意义
定义函数的三种形式:
1.无参:应用场景仅仅只是执行一些操作,比如与用户交互,打印
2.有参:需要根据外部传进来的参数,才能执行相应的逻辑,比如统计长度,求最大值最小值
#定义阶段
def calc(x,y): #有参数
print(x*y)
def tell_msg(): #无参数
print('hello world')
#调用阶段
calc(5,8)
tell_msg()
#打印结果
40
hello world
#结论:#1、定义时无参,意味着调用时也无需传入参数
#2、定义时有参,意味着调用时则必须传入参数
3.空函数:设计代码结构
def auth(user,password):
'''
auth function
:param user: 用户名
:param password: 密码
:return: 认证结果
'''
pass
def get(filename):
'''
:param filename:
:return:
'''
pass
def put(filename):
'''
:param filename:
:return:
'''
def ls(dirname):
'''
:param dirname:
:return:
'''
pass
三,函数使用规则:先调用,再调用
函数即“变量”,“变量”必须先定义后引用。未定义而直接引用函数,就相当于在引用一个不存在的变量名
#test1
def foo():
print('from foo')
bar()
foo() #报错
#test2
def bar():
print('from bar')
def foo():
print('from foo')
bar()
foo() #正常
#test3
def foo():
print('from foo')
bar()
def bar():
print('from bar')
foo() #正常
#结论:函数的使用,必须遵循原则:先定义,后调用
#我们在使用函数时,一定要明确地区分定义阶段和调用阶段
#定义阶段
def foo():
print('from foo')
bar()
def bar():
print('from bar')
#调用阶段
foo()
def foo():
print('from foo')
bar()
foo()
def bar():
print('from bar')
#报错
四,函数与过程
1.函数返回值
①无return->None
②return 1个值->返回1个值
③return 逗号分隔多个值->元组
def test01():
pass
def test02():
return 0
def test03():
return 0,10,'hello',['alex','lb'],{'WuDaLang':'lb'}
t1=test01()
t2=test02()
t3=test03()
print('from test01 return is [%s]: ' % type(t1),t1)
print('from test02 return is [%s]: ' % type(t2),t2)
print('from test03 return is [%s]: ' % type(t3),t3)
2.过程定义:过程就是简单特殊没有‘返回值’的函数,没有return,默认的返回值为None
def test01():
msg='hello The little green frog'
print(msg)
def test02():
msg='hello WuDaLang'
print(msg)
return msg
t1=test01()
t2=test02()
print('from test01 return is [%s]' % t1)
print('from test02 return is [%s]' % t2)
五,参数
1.形参与实参
①形参变量只有在被调用时才分配内存单元,在调用结束时,即刻释放所分配的内存单元。因此,形参只在函数内部有效。
函数调用结束返回主调用函数后则不能再使用该形参变量
②实参可以是常量、变量、表达式、函数等,无论实参是何种类型的量,在进行函数调用时,它们都必须有确定的值,
以便把这些值传送给形参。因此应预先用赋值,输入等办法使参数获得确定值
def calc(x,y):
res =x*y
return res
c = calc(5,8)
print(c)
2.位置参数与关键字参数
①位置参数,必须一一对应,缺一行不行,多一行也不行
②关键字参数,无需一一对应,缺一行也不行,多一行也不行
③位置参数必须在关键字参数前面
3.默认参数
def handle(x,type='mysql'):
print(x)
print(type)
#handle('hello')
#handle('hello',type='sqlite')
#handle('hello','sqlite')
打印:
hello
sqlite
4.参数组
*:将参数组打包成元组形式
def test(x,*args): #传入多个参数
print(x)
print(args)
test(1,2,3,4,5,6)
打印:
1
(2, 3, 4, 5, 6)
test(1)
打印:
1
()
#传入字典参数
def test(x,*args):
print(x)
print(args)
test(1,{'name':'alex'})
打印:
1
({'name': 'alex'},)
#传入列表参数
def test(x,*args):
print(x)
print(args)
print(args[0][0])
test(1,['x','y','z'])
打印:
1
(['x', 'y', 'z'],)
x
#传入打包好的列表,解包成元组形式
def test(x,*args):
print(x)
print(args)
test(1,*['x','y','z'])
打印:
1
('x', 'y', 'z')
#传入打包好的元组,解包成元组形式
def test(x,*args):
print(x)
print(args)
test(1,*('x','y','z'))
打印:
1
('x', 'y', 'z')
*针对位置参数
例如:
def test(x,*args):
print(x)
print(args)
test(1,y=2,z=3)
打印:报错
TypeError: test() got an unexpected keyword argument 'y'
**:将参数组打包成字典形式
def test(x,**kwargs):
print(x)
print(kwargs)
test(1,y=2,z=3)
#test(1,y=2,z=3,z=4) #报错:一个参数不能传两个值
打印:
1
{'y': 2, 'z': 3}
1
#传入键值对
def test(x,*args,**kwargs):
print(x)
print(args)
print(kwargs)
test(1,2,3,4,5,6,8,1,y=1,z=1)
打印:
1
(2, 3, 4, 5, 6, 8, 1)
{'y': 1, 'z': 1}
def test(x,*args,**kwargs):
print(x)
print(args,args[1])
print(kwargs,kwargs['y'])
test(1,2,3,4,5,6,8,1,y=1,z=1)
打印:
1
(2, 3, 4, 5, 6, 8, 1) 3
{'y': 1, 'z': 1} 1
def test(x,*args,**kwargs):
print(x)
print(args,args[1])
print(kwargs,kwargs.get('y'))
test(1,*[1,2,3],**{'y':1})
打印:
1
(1, 2, 3) 2
{'y': 1} 1
六,函数对象
1.函数是第一类对象,即函数可以当作数据传递
①可以被引用
②可以当作参数传递
③返回值可以是函数
④可以当作容器类型的元素
2.利用该特性,优雅的取代多分支的if
def foo():
print('foo')
def bar():
print('bar')
dic={
'foo':foo,
'bar':bar,
}
while True:
choice=input('>>: ').strip()
if choice in dic:
dic[choice]()
七,嵌套和作用域
1.嵌套定义
def f1():
def f2():
def f3():
print('from f3')
f3()
f2()
f1()
f3() #报错
2.函数嵌套
name = "Alex"
def change_name():
name = "Alex2"
def change_name2():
name = "Alex3"
print("第3层打印",name)
change_name2() #调用内层函数
print("第2层打印",name)
change_name()
print("最外层打印",name)
3.作用域
①作用域即范围
- 全局范围
- 局部范围
②作用域关系是在函数定义阶段就已经固定的,与函数的调用位置无关,如下:
x=1
def f1():
def f2():
print(x)
return f2
x=100
def f3(func):
x=2
func()
x=10000
f3(f1())
例一:
name='alex'
def foo():
name='lhf'
def bar():
print(name)
return bar
func=foo()
func()
例二:
name='alex'
def foo():
name='lhf'
def bar():
name='wupeiqi'
def tt():
print(name)
return tt
return bar
func=foo()
func()()
③查看作用域:globals(),locals()
LEGB 代表名字查找顺序: locals -> enclosing function -> globals -> __builtins__
locals 是函数内的名字空间,包括局部变量和形参
enclosing 外部嵌套函数的名字空间(闭包中常见)
globals 全局变量,函数定义所在模块的名字空间
builtins 内置模块的名字空间
八,局部变量和全局变量
①在子程序中定义的变量称为局部变量,在程序的一开始定义的变量称为全局变量。
②全局变量作用域是整个程序,局部变量作用域是定义该变量的子程序。
③当全局变量与局部变量同名时-->>在定义局部变量的子程序内,局部变量起作用;在其它地方全局变量起作用
name='lhf'
def change_name():
print('我的名字',name)
change_name()
def change_name():
name='帅了一笔'
print('我的名字',name)
change_name()
print(name)
def change_name():
global name
name='帅了一笔'
print('我的名字',name)
change_name()
九,关键字global和nonlocal
如果函数中无global关键字,优先读取局部变量,能读取全局变量,无法对全局变量重新赋值:
对可变类型,可以对内部元素进行操作
2.无声明局部变量
如果函数中有global关键字,变量本质上就是全局的那个变量,可读取可赋值:
1.有声明局部变量
2.无声明局部变量
建议:
全局变量用大写字母 局部变量用小写字母
NAME = '大山'
def meinv():
name = 'huang'
print(name)
def shuaige():
name = 'chen'
print(name)
def jiyou():
name = 'zhao'
print(name)
jiyou()
print(name)
shuaige()
print(name)
meinv()
#例2
name = '度娘'
def weibo():
name = 'jiyou'
def weibobo():
global name
name = 'baihe'
weibobo()
print(name)
print(name)
weibo()
print(name)
#例3
name = '度娘'
def weibo():
name = 'jiyou'
def weibobo():
nonlocal name #nonlocal关键字,指定上一层变量
name = 'baihe'
weibobo()
print(name)
print(name)
weibo()
print(name)
十,递归
递归调用是函数嵌套调用的一种特殊形式,函数在调用时,直接或间接调用了自身,就是递归调用
递归特性:
1. 必须有一个明确的结束条件
2. 每次进入更深一层递归时,问题规模相比上次递归都应有所减少
3. 递归效率不高,递归层次过多会导致栈溢出(在计算机中,函数调用是通过栈(stack)这种数据结构实现的,每当进入一个
函数调用,栈就会加一层栈帧,每当函数返回,栈就会减一层栈帧。由于栈的大小不是无限的,所以,递归调用的次数过多,会
导致栈溢出)
递归调用应该包含两个明确的阶段:回溯,递推
回溯就是从外向里一层一层递归调用下去
回溯阶段必须要有一个明确地结束条件,每进入下一次递归时,问题的规模都应该有所减少(否则,单纯地重复调用自身是毫无意义的)
# salary(5)=salary(4)+300
# salary(4)=salary(3)+300
# salary(3)=salary(2)+300
# salary(2)=salary(1)+300
# salary(1)=100
#
# salary(n)=salary(n-1)+300 n>1
# salary(1) =100 n=1
#定义一个函数完成上述过程def salary(n):
if n == 1:
return 100
return salary(n-1)+300
print(salary(5))
问题:python中的递归效率低,需要在进入下一次递归时保留当前的状态,在其他语言中可以有解决方法:尾递归优化,即在函数的最后一步(而非最后一行)调用自己
def calc(n):
print(n)
if int(n/2) == 0:
return n
return calc(int(n/2))
res = calc(10)
print(res)
打印结果:
10
5
2
1
1
import time
name_list = ['鸡总','老司机','老王','游总']
def request_av(name_list):
if len(name_list) == 0:
return '没人有资源'
person = name_list.pop(0)
if person == '老王':
return '你要的资源在我的网盘,网盘号为xxxxx'
print('饥渴男问:请问你有没有资源')
print('%s回答:我没有资源,但是你可以找%s' % (person,name_list))
time.sleep(5)
res = request_av(name_list)
return res
res = request_av(name_list)
print(res)
ls = []
def test(n):
n = int(n/2)
ls.append(n)
if int(n/2) == 1:
return ls
return test(n)
print(test(101))
二分法-->>递归应用实例
想从一个按照从小到大排列的数字列表中找到指定的数字,遍历的效率太低,用二分法(算法的一种,算法是解决问题的方法)可以极大低缩小问题规模
data = [1, 3, 6, 7, 9, 12, 14, 16, 17, 18, 20, 21, 22, 23, 30, 32, 33, 35]
def datacheck(dataset,find_num):
if len(dataset) > 1:
print('你要的数字可能有')
mid = int(len(dataset)/2)
if dataset[mid] == find_num:
print('找到了')
elif dataset[mid] > find_num:
print('数字在%s范围内' % dataset[0:mid])
return datacheck(dataset[0:mid],find_num)
else:
print('数字在%s范围内' % dataset[mid:len(dataset)-1])
return datacheck(dataset[mid:len(dataset)-1],find_num)
else:
if dataset[0] == find_num:
print('找到数字了')
else:
print('没有其他的了')
datacheck(data,6)
data = [1, 3, 6, 7, 9, 12, 14, 16, 17, 18, 20, 21, 22, 23, 30, 32, 33, 35]
def data_search(data,find_num,start=0,stop=len(data)-1):
if start <= stop:
mid = (start+(stop-start))//2
if find_num > data[mid]:
start = mid+1
elif find_num < data[mid]:
stop = mid-1
else:
print('数字找到了-->>%s' % data[mid])
return data[mid]
return data_search(data,find_num,start,stop)
else:
print('没有了')
data_search(data,7)
十一,匿名函数-->>lambda关键字
def func(x,y,z=1): #正常定义的函数
return x+y+z
#匿名函数
lambda x,y,z=1:x+y+z #与函数有相同的作用域,但是匿名意味着引用计数为0,使用一次就释放,除非让其有名字
func=lambda x,y,z=1:x+y+z
func(1,2,3)
#让其有名字就没有意义
name = 'alex'
def change_name(x):
return name+'_sb'
res = change_name(name)
print(res)
f = lambda x:name+'_sb'
print(f(name))
func = lambda x:x+'_sb'
res = func(name)
print(res)
---------------------------------------------------
#lambda不会去单独使用
#func = lambda x,y,z:x+y+z
#print(func(1,2,3))
name1 = 'alex'
name2 = 'sbalex'
name3 = 'superalex'
f = lambda x,y,z:(x+1,y+1,z+1)
print(f(1,1,1))
---------------------------------------------------
#与其他函数搭配使用
l=[3,2,100,999,213,1111,31121,333]
print(max(l))
dic={'k1':10,'k2':100,'k3':30}
print(max(dic))
print(dic[max(dic,key=lambda k:dic[k])])
------------------------
res = map(lambda x:x**2,[1,5,7,4,8])
for i in res:
print(i)
输出
1
25
49
16
64
十二,内置函数
>>> dir(__builtins__)
['ArithmeticError', 'AssertionError', 'AttributeError', 'BaseException', 'BlockingIOError', 'BrokenPipeError', 'BufferError', 'BytesWarning', 'ChildProcessError', 'ConnectionAbortedError', 'ConnectionError', 'ConnectionRefusedError', 'ConnectionResetError', 'DeprecationWarning', 'EOFError', 'Ellipsis', 'EnvironmentError', 'Exception', 'False', 'FileExistsError', 'FileNotFoundError', 'FloatingPointError', 'FutureWarning', 'GeneratorExit', 'IOError', 'ImportError', 'ImportWarning', 'IndentationError', 'IndexError', 'InterruptedError', 'IsADirectoryError', 'KeyError', 'KeyboardInterrupt', 'LookupError', 'MemoryError', 'ModuleNotFoundError', 'NameError', 'None', 'NotADirectoryError', 'NotImplemented', 'NotImplementedError', 'OSError', 'OverflowError', 'PendingDeprecationWarning', 'PermissionError', 'ProcessLookupError', 'RecursionError', 'ReferenceError', 'ResourceWarning', 'RuntimeError', 'RuntimeWarning', 'StopAsyncIteration', 'StopIteration', 'SyntaxError', 'SyntaxWarning', 'SystemError', 'SystemExit', 'TabError', 'TimeoutError', 'True', 'TypeError', 'UnboundLocalError', 'UnicodeDecodeError', 'UnicodeEncodeError', 'UnicodeError', 'UnicodeTranslateError', 'UnicodeWarning', 'UserWarning', 'ValueError', 'Warning', 'WindowsError', 'ZeroDivisionError', '__build_class__', '__debug__', '__doc__', '__import__', '__loader__', '__name__', '__package__', '__spec__', 'abs', 'all', 'any', 'ascii', 'bin', 'bool', 'bytearray', 'bytes', 'callable', 'chr', 'classmethod', 'compile', 'complex', 'copyright', 'credits', 'delattr', 'dict', 'dir', 'divmod', 'enumerate', 'eval', 'exec', 'exit', 'filter', 'float', 'format', 'frozenset', 'getattr', 'globals', 'hasattr', 'hash', 'help', 'hex', 'id', 'input', 'int', 'isinstance', 'issubclass', 'iter', 'len', 'license', 'list', 'locals', 'map', 'max', 'memoryview', 'min', 'next', 'object', 'oct', 'open', 'ord', 'pow', 'print', 'property', 'quit', 'range', 'repr', 'reversed', 'round', 'set', 'setattr', 'slice', 'sorted', 'staticmethod', 'str', 'sum', 'super', 'tuple', 'type', 'vars', 'zip']
1.map() -->>处理序列中的每个元素,得到的结果是一个列表,该列表的元素个数与原来一样
#正常实现
num_1 = [1,2,3,4]
ret = []
for i in num_1:
ret.append(i**2)
print(ret)
#将这个过程封装成一个函数
num_1 = [1,2,3,4]
def map_test(array):
ret = []
for i in array:
ret.append(i**2)
return ret
res = map_test(num_1)
print(res)
#将想要的方法列入函数的参数,如需实现该种方法,直接将方法对应的函数作为参数传入即可
num_1 = [1,2,3,4]
def add_one(x):
return x+1
def remove_one(x):
return x-1
def pf(x):
return x**2
def map_test(func,array):
ret = []
for i in array:
ret.append(func(i))
return ret
print(map_test(remove_one,num_1))
print(map_test(add_one,num_1))
print(map_test(pf,num_1))
#当然也可以使用lambda关键字
num_1 = [1,2,3,4]
def map_test(func,array):
ret = []
for i in array:
ret.append(func(i))
return ret
print(map_test(lambda x:x-1,num_1))
print(map_test(lambda x:x+1,num_1))
print(map_test(lambda x:x**2,num_1))
#使用map()内置函数
num_1 = [1,2,3,4]
def map_test(func,array):
ret = []
for i in array:
ret.append(func(i))
return ret
res = map_test(lambda x:x+1,num_1)
print(res)
rea = map(lambda x:x+1,num_1) #map()第二个参数为可迭代对象,map()的结果是可迭代对象
print(rea)
for i in rea:
print(i)
print(list(rea))
2.filter() -->>遍历序列中的每个元素,判断每个元素的布尔值,如果是True则留下来
#将这个过程封装成一个函数
shuai_ge = ['sb_ji','sb_lao','sb_you','sb_wang','huang']
def filter_test(array):
ret = []
for each in array:
if not each.startswith('sb'):
ret.append(each)
return ret
print(filter_test(shuai_ge))
#将想要的方法列入函数的参数,如需实现该种方法,直接将方法对应的函数作为参数传入即可
shuai_ge = ['sb_ji_he','sb_lao_he','sb_you_he','sb_wang_he','huang']
def sb_show1(x):
return x.endswith('he')
def sb_show2(x):
return x.startswith('sb')
def filter_test(func,array):
ret = []
for each in array:
if not func(each):
ret.append(each)
return ret
print(filter_test(sb_show1,shuai_ge))
print(filter_test(sb_show2,shuai_ge))
#当然也可以使用lambda关键字
shuai_ge = ['sb_ji_he','sb_lao_he','sb_you_he','sb_wang_he','huang']
def filter_test(func,array):
ret = []
for each in array:
if not func(each):
ret.append(each)
return ret
print(filter_test(lambda x:x.startswith('sb'),shuai_ge))
print(filter_test(lambda x:x.endswith('he'),shuai_ge))
#使用filter()内置函数
shuai_ge = ['sb_ji_he','sb_lao_he','sb_you_he','sb_wang_he','huang']
def filter_test(func,array):
ret = []
for each in array:
if not func(each):
ret.append(each)
return ret
print(filter_test(lambda x:x.startswith('sb'),shuai_ge))
#map()第二个参数为可迭代对象,map()的结果是可迭代对象
res = filter(lambda x:not x.startswith('sb'),shuai_ge)
print(res)
for i in res:
print(i)
print(list(res))
3.reduce()
其语法格式: reduce ( func , seq [ , init ] )
reduce函数过程:每次迭代,将上一次的迭代结果(第一次时为init的元素,如没有init则为seq的第一个元素)与下一个元素一同执行一个二元的func函数。在reduce函数中,init是可选的,如果使用,则作为第一次迭代的第一个元素使用。
#正常实现
num_1 = [1,2,3,100]
res = 0
for num in num_1:
res += num
print(res)
#将这个过程封装成一个函数
num_1 = [1,2,3,100]
def reduce_test(array):
res = 0
for num in array:
res += num
return res
print(reduce_test(num_1))
#将一个功能函数作为参数传入
num_1 = [1,2,3,100]
def multi(x,y):
return x*y
def reduce_test(func,array):
res = array.pop(0)
for num in array:
res= func(res,num)
return res
print(reduce_test(multi,num_1))
#增加init初始值
num_1 = [1,2,3,100]
def multi(x,y):
return x*y
#lambda x,y:x*y
def reduce_test(func,array,init=None):#增加一个初始值参数
if init is None:
res = array.pop(0)
else:
res = init
for num in array:
res= func(res,num)
return res
print(reduce_test(multi,num_1,100))
print(reduce_test(lambda x,y:x*y,num_1,100))
#reduce()函数
from functools import reduce
num_1 = [1,2,3,100]
print(reduce(lambda x,y:x+y,num_1,1))
print(reduce(lambda x,y:x+y,num_1))
print(reduce(lambda x,y:x*y,num_1,100))
print(reduce(lambda x,y:x*y,num_1))
总结:
#当然了,map,filter,reduce,可以处理所有数据类型
name_dic=[
{'name':'alex','age':1000},
{'name':'wupeiqi','age':10000},
{'name':'yuanhao','age':9000},
{'name':'linhaifeng','age':18},
]
#利用filter过滤掉千年王八,万年龟,还有一个九千岁
def func(x):
age_list=[1000,10000,9000]
return x['age'] not in age_list
res=filter(func,name_dic)
for i in res:
print(i)
res=filter(lambda x:x['age'] == 18,name_dic)
for i in res:
print(i)
#reduce用来计算1到100的和
from functools import reduce
print(reduce(lambda x,y:x+y,range(100),100))
print(reduce(lambda x,y:x+y,range(1,101)))
#用map来处理字符串列表啊,把列表中所有人都变成sb,比方alex_sb
name=['alex','laowang','jiba']
res=map(lambda x:x+'_sb',name)
for i in res:
print(i)
其他内置函数
#abs -->>绝对值
print(abs(-1))
print(abs(1))
#all -->>将可迭代对象的每个元素逐一判断,如果都不为空或0,结果为布尔值True,反之为False,若迭代对象为空,也返回True
print(all([1,2,'1']))
print(all((1,2,'1')))
print(all([1,2,0]))
print(all(['hello']))
print(all(''))
print(all([]))
#any -->>与all相反,只要有一个元素不为0就返回True
print(any([0,'']))
print(any((0,'',1)))
print(any([0,'',1]))
#bin -->>将十进制改为二进制
print(bin(3))
#bool() -->>空,None,0的布尔值为False,其余的都为True
print(bool(''))
print(bool(None))
print(bool(0))
print(bool(1))
#bytes -->>将字符串转换成字节形式 注意编码与解码的格式要一样
name = '你好'
print(bytes(name,encoding='utf-8'))
print(bytes(name,encoding='utf-8').decode())
print(bytes(name,encoding='gbk'))
#print(bytes(name,encoding='gbk').decode()) -->>python3默认解码格式为utf-8,报错
print(bytes(name,encoding='gbk').decode('gbk'))
#chr -->>按照ascii表来转化
print(chr(97))
print(chr(45))
#divmod -->>计算两者相除,结果为商和余数
print(divmod(10,2))
print(divmod(10,3))
#eval
#1.去掉字符串引号,将数据结构提取出来
#2.计算字符串中的表达式的值
name = '{"name":"huang"}'
a = eval(name)
print(a)
print(a['name'])
ex = '1+2*2'
b = eval(ex)
print(b)
#可hash的数据类型为不可变数据类型,不可hash的数据类型即可变数据类型
#hash() 进行哈希计算,得到一个哈希值,不论参数多长,得到的哈希值的长度是固定的
#只要参数变量不变,得到的哈希值是固定的,不能根据哈希值推导到原变量值
name = 'alex'
print(hash(name))
name ='Tom'
print(hash(name))
#hex -->>十进制转换成十六进制
print(bin(10)) #-->>10进制->2进制
print(hex(12)) #-->>10进制->16进制
print(oct(12)) #-->>10进制->8进制
max()&min()&sorted()
#字典的运算:最大值,最小值,排序
salaries={
'egon':3000,
'alex':100000000,
'wupeiqi':10000,
'yuanhao':2000
}
#迭代字典,取得的是key,因此比较key的最大值和最小值
res = max(salaries)
print(res)
res = min(salaries)
print(res)
#取values来比较
res = max(salaries.values())
print(res)
res = min(salaries.values())
print(res)
#想办法去除工资最高的人名,即比较值,得到键
res = max(salaries,key=lambda k:salaries[k])
print(res)
res = min(salaries,key=lambda k:salaries[k])
print(res)
#也可以通过zip实现
salaries_and_names = zip(salaries.values(),salaries.keys())
res = max(salaries_and_names)
print(res)
#salaries_and_names是迭代器,因此只能访问一次,因此min()出错
res = min(salaries_and_names)
print(res)
#sorted实现排序
l1 = [1,5,82,4,15,60]
res = sorted(l1,key=None,reverse=False)
print(res)
print(l1)
#将reverse值改为Ture,实现排序加翻转
l2 = [1,5,82,4,15,60]
res = sorted(l2,key=None,reverse=True)
print(res)
print(l2)
作业题:
写函数,计算传入字符串中数字、字母、空格 以及 其他的个数
def modify_file(filename,old,new):
import os
with open(filename,'r',encoding='utf-8') as read_f,\
open('filename','w',encoding='utf-8') as write_f:
for line in read_f:
if old in line:
line=line.replace(old,new)
write_f.write(line)
os.remove(filename)
os.rename('.bak.swap',filename)
modify_file('1234.txt','value','key')
写函数,计算传入字符串中【数字】、【字母】、【空格】以及 【其他】的个数
def check_data(msg):
data = {
'数字':0,
'字母':0,
'空格':0,
'其他':0
}
for i in msg:
if i.isdigit():
data['数字'] += 1
elif i.isalpha():
data['字母'] += 1
elif i.isspace():
data['空格'] += 1
else:
data['其他'] += 1
return data
res = check_data('sfsfsfsfs1221213')
print(res)
写函数,判断用户传入的对象(字符串、列表、元组)长度是否大于5。
def check_length(data):
length = len(data)
if len(data) > 5:
print('%s长度大于5' % type(data))
else:
print('你的长度不足哦')
check_length('afafafasfaf')
写函数,检查传入列表的长度,如果大于2,那么仅保留前两个长度的内容,并将新内容返回给调用者。
def check_length(l):
length = len(l)
if length > 2:
l = l[0:2]
return l
res = check_length([1,2,3,4,5])
print(res)
写函数,检查获取传入列表或元组对象的所有奇数位索引对应的元素,并将其作为新列表返回给调用者。
第一种
def check_lset(data):
length = len(data)
ls = []
for i in range(length+1):
if not i%2 == 0:
ls.append(data[i])
return ls
res = check_lset([1,5,6,7,9,1,5,8])
print(res)
第二种
def func2(seq):
return seq[::2]
print(func2([1,2,3,4,5,6,7]))
写函数,检查字典的每一个value的长度,如果大于2,那么仅保留前两个长度的内容,并将新内容返回给调用者。
dic = {"k1": "v1v1", "k2": [11,22,33,44]}
PS:字典中的value只能是字符串或列表
dic = {"k1":"v1v1", "k2":[11,22,33,44],"k3":(1,2)}
def func1(seq):
dv = {}
for k,v in seq.items():
if len(v) > 2:
dv[k] = v[0:2]
return dv
res = func1(dic)
print(dic)
#用map来处理字符串列表啊,把列表中所有人都变成sb,比方alex_sb
name=['alex','heheda','liuliuda']
#用map来处理下述l,然后用list得到一个新的列表,列表中每个人的名字都是sb结尾
>>> l=[{'name':'alex'},{'name':'y'}]
>>> x=map(lambda i:{'name':i['name']+'sb'},l)
>>> for i in x:
... print(i)
...
{'name': 'alexsb'}
{'name': 'ysb'}
#用filter来处理,得到股票价格大于20的股票名字
shares={
'IBM':36.6,
'Lenovo':23.2,
'oldboy':21.2,
'ocean':10.2,
}
>>> f=filter(lambda k:shares[k]>20,shares)
>>> list(f)
['IBM', 'Lenovo', 'oldboy']
#如下,每个小字典的name对应股票名字,shares对应多少股,price对应股票的价格
l = [
{'name': 'IBM', 'shares': 100, 'price': 91.1},
{'name': 'AAPL', 'shares': 50, 'price': 543.22},
{'name': 'FB', 'shares': 200, 'price': 21.09},
{'name': 'HPQ', 'shares': 35, 'price': 31.75},
{'name': 'YHOO', 'shares': 45, 'price': 16.35},
{'name': 'ACME', 'shares': 75, 'price': 115.65}
]
1:map来得出一个包含数字的迭代器,数字指的是:购买每支股票的总价格
>>> m=map(lambda item:item['shares']*item['price'],l)
2:基于1的结果,用reduce来计算,购买这些股票总共花了多少钱
>>> r=reduce(lambda x,y:x+y,m)
>>> r
51009.75
3:用filter过滤出,单价大于100的股票有哪些
>>> f=filter(lambda item:item['price'] > 100,l)
1、文件内容如下,标题为:姓名,性别,年纪,薪资
egon male 18 3000
alex male 38 30000
wupeiqi female 28 20000
yuanhao female 28 10000
要求:
从文件中取出每一条记录放入列表中,
列表的每个元素都是{'name':'egon','sex':'male','age':18,'salary':3000}的形式
2 根据1得到的列表,取出薪资最高的人的信息
3 根据1得到的列表,取出最年轻的人的信息
4 根据1得到的列表,将每个人的信息中的名字映射成首字母大写的形式
5 根据1得到的列表,过滤掉名字以a开头的人的信息
6 一个嵌套很多层的列表,如l=[1,2,[3,[4,5,6,[7,8,[9,10,[11,12,13,[14,15]]]]]]],用递归取出所有的值
#1
with open('123.txt','r',encoding='utf-8') as f:
items = (line.split() for line in f)
print(items)
info = [{'name':name,'sex':sex,'age':age,'salary':salary} \
for name,sex,age,salary in items]
print(info)
#2
print(max(info,key=lambda dic:dic['salary']))
#3
print(min(info,key=lambda dic:dic['age']))
#4
info_new1 = map(lambda item:{'name':item['name'].capitalize(),
'sex':item['sex'],
'age':item['age'],
'salary':item['salary']},info)
print(list(info_new1))
#5
info_new2 = filter(lambda item:item['name'].startswith('a'),info)
print(list(info_new2))
#6
l=[1,2,[3,[4,5,6,[7,8,[9,10,[11,12,13,[14,15]]]]]]]
def get_all(l):
for i in l:
if type(i) == int:
print(i)
else:
return get_all(i)
res = get_all(l)
print(res)