6.1 懒惰即美德
6.2 抽象和结构
6.3 创建函数
def:定义函数
内建函数callable:可以用来判断函数是否可调用
>>> import math
>>> x=1
>>> y=math.sqrt
>>> callable(x)
False
>>> callable(y)
True
6.3.1 文档化函数
两种方式:注释、字符串
doc:可以查看函数说明
或者使用help:获得相关信息
>>> def addition(x,y):
... 'Conputer the sum of x and y'
... #hello
... return x+y
...
>>> addition.__doc__
'Conputer the sum of x and y'
>>> help(addition)
Help on function addition in module __main__:
addition(x, y)
Conputer the sum of x and y
6.3.2 并非真正的函数
不管有没有return,python的函数都会返回值,至少会返回None
6.4 参数魔法
6.4.1 值从哪里来
实参和形参
6.4.2 我能改变参数吗
1.为什么要修改参数
例子:名字的存取
def init(data):
data['first']={}
data['middle']={}
data['last']={}
def lookup(data,label,name):
return data[label].get(name)
def store(data,full_name):
names=full_name.split()
if len(names)==2:names.insert(1,'')
labels='first','middle','last'
for label,name in zip(labels,names):
people=lookup(data,label,name)
if people:
people.append(full_name)
else:
data[label][name]=[full_name]
Mynames={}
init(Mynames)
store(Mynames,'Robin Hood')
store(Mynames,'Robin Loksy')
store(Mynames,'Mr. Gumby')
print lookup(Mynames,'middle','')
2.如果我的参数不可变呢
可使用列表或者函数返回再赋值
6.4.3 关键字参数和默认值
在调用函数我们可以使用(参数名+值)来回避位置问题
def hello(greeting,name):
print greeting+','+name
hello(name='jack!',greeting='hello')#参数不受前后顺序的限制
还可以给参数设置默认值
6.4.4 收集参数
带*号的参数:收集剩余位置的参数放在一个元组里
如果要处理关键字参数则使用**:放在字典里
def print_params(x,y,z=3,*pospar,**keypar):
print x,y,z
print pospar
print keypar
print_params(1,2,3,5,6,7,foo=1,bar=2)
1 2 3
(5, 6, 7)
{'foo': 1, 'bar': 2}
6.4.5 参数收集的逆过程
params={'name':'Sir Robin','greeting':'Well met'}
hell(**params)
元组或列表用:* 字典用:**
6.4.6 练习
6.5 作用域
globals:返回全局变量值
locals:返回局部变量的字典
vars:返回全局变量的字典
嵌套作用域:
def multiplier(factor):
def multiplyByFactor(number):
return number*factor
return multiplyByFactor
>>>double=multiplier(2)
>>>double(5)
>>>10
外层循环返回里层循环,但是并没有调用,它“带着”它的环境
6.6 递归
6.6.1 两个经典:阶乘和幂
#n的阶乘
def factorial(n):
if n==1:
return 1
else: return n*factorial(n-1)
#二分查找
def search(sequence,number,lower,upper):
if lower==upper:
assert number==sequence[upper]#检查是否相等,如果这个时候还不相等则找不到,干掉程序,相等返回upper
return upper
else:
middle=(lower+upper)//2
if number>sequence[middle]:
return search(sequence,number,middle+1,upper)
else:
return search(sequence,number,lower,middle)
函数式编程:
map、filter、reduce
map和filter可以轻易被列表推导式代替,基本没什么大的用处,reduce虽然不能轻易被替代,但是很少用到
>>> number=[1,2,3,4,5,6]
>>> reduce(lambda x,y:x+y,number)
21
首先从列表里取前两个数,然后执行x+y,然后将结果当成x,再从列表里取出一个数当做y,直到列表的数据全被处理
本章新函数
map(func,seq[,seq,…]):对序列中的每个元素应用函数
filter(func,seq):返回其函数为真的元素的列表
reduce(func,seq[,initial]):等同于func(func(seq[0].seq[1]),seq[2]….)
sum(seq):列表求和
apply(func[,args[,kwargs]]):调用函数,参数从元组或字典里取