《Python基础教程》读书笔记(1)之第6章抽象(关键词:Python/抽象/函数/参数/作用域)
2017-09-14 13:45
573 查看
第6章 抽象
6.3 创建函数
6.3.1 记录函数
如果在函数的开头写下字符串,它就会作为函数的一部分进行存储,称为“文档字符串”。 如下代码演示了如何给函数添加文档字符串:
def fibs(num): 'i am a fib function' result = [0, 1] for i in range(num-2): result.append(result[-2] + result[-1]) return result
文档字符串可以按如下方式访问:
>>> fibs.__doc__ 'i am a fib function'
注意 `__doc__`是函数属性。 内建的help函数是非常有用的。在交互式解释器中国使用它,可以得到关于函数,包括它的文档字符串的信息:
>>> help(fibs) Help on function fibs in module __main__: fibs(num) i am a fib function
6.4 参数魔法
6.4.2 我能改变参数吗
在函数内为参数赋予新值,不会改变任何外部变量的值:
>>> def try_to_change(n): ... n = 'gumby' ... >>> name = 'henry' >>> try_to_change(name) >>> name 'henry'
在try_to_change内,参数n获得了新值,但是它没有影响到name变量。n实际上是个完全不同的变量,具体的工作方式类似于下面:
>>> name = 'henry' >>> n = name >>> n = 'gumby' >>> name 'henry'
当变量n改变的时候,变量name不变。 同样,当在函数内部把参数重绑定(赋值)的时候,函数外的变量不会受到影响。 注意 参数存储在局部作用域(local scope)内。 字符串(以及数字和元组)是不可变的,即无法修改(也就是说只能用新的值覆盖)。
1. 为什么我想修改参数
抽象的要点就是隐藏更新时的繁琐的细节,这个过程可以用函数实现。 下面的例子就是初始化数据结构的函数:
>>> def init(data): ... data['first'] = {} ... data['middle'] = {} ... data['last'] = {}
上面的代码只是把初始化语句放到了函数中,使用方法如下:
>>> storage = {} >>> init(storage) >>> storage {'middle': {}, 'last': {}, 'first': {}}
可以看到,函数包办了初始化的工作,让代码更易读。 注意 字典的键并没有具体的顺序,所以当字典打印出来的时候,顺序是不同的。
如果我的参数不可变呢
函数只能修改参数对象本身。
6.4.4 收集参数
*的意思是“收集其余的位置参数”。
>>> def print_params_2(title, *params): ... print title ... print params ... >>> print_params_2('Params:', 1, 2, 3) Params: (1, 2, 3)
但是,不能处理关键字参数:
>>> print_params_2('...', something=42) Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: print_params_2() got an unexpected keyword argument 'something'
所以,我们需要一个能处理关键字参数的“收集”操作。
>>> def print_params_4(x, y, z=3, *pospar, **keypar): ... print x, y, z ... print pospar ... print keypar ... >>> print_params_4(1, 2, 3, 5, 6, 7, foo=1, bar=2) 1 2 3 (5, 6, 7) {'foo': 1, 'bar': 2}
6.5 作用域
可以把变量看作是值的名字。在执行x=1赋值语句后,名称x引用到值1。这就像用字典一样,键引用值。变量和所对应的值用的是个“不可见”的字典。实际上这么说已经很接近真实的情况了。内建的vars函数可以返回这个字典:>>> x = 1 >>> vars() {'me': 'magnus lie hetland', 'x': 1, 'name': 'henry', 'power': <function power at 0x7fbb03b94b90>, '__builtins__': <module '__builtin__' (built-in)>, 'storage': {'middle': {}, 'last': {}, 'first': {}}, 'try_to_change': <function try_to_change at 0x7fbb03b94938>, '__package__': None, 'init': <function init at 0x7fbb03b949b0>, 'lookup': <function lookup at 0x7fbb03b94a28>, 'print_params_4': <function print_params_4 at 0x7fbb03b94b18>, '__name__': '__main__', 'n': 'gumby', '__doc__': None, 'print_params_2': <function print_params_2 at 0x7fbb03b94aa0>} >>> vars()['x'] 1 >>> scope = vars() >>> scope['x'] 1 >>> scope['x'] += 1 >>> x 2
警告 一般来说,vars所返回的字典是不能修改的,因为根据官方的Python文档的说法,结果是未定义的。换句话说,可能得不到想要的结果。
这类“不可见字典”叫做命名空间或者作用域。那么到底有多少个命名空间?除了全局作用域外,每个函数调用都会创建一个新的作用域:
嵌套作用域
闭包(closure)
6.6 递归
6.6.2 另外一个经典:二元查找
实现一个二分查找算法:# biSearchDemo.py def search(sequence, number, lower, upper=None): if upper is None: upper = len(sequence) - 1 if lower == upper: assert number == sequence[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)
提示 标准库中的bisect模块可以非常有效地实现二元查找。
参考文献:
1.《Pytho基础教程(第2版·修订版)》。
相关文章推荐
- 20161016 Python 读书笔记之函数抽象 参数、作用域
- Python基础教程--抽象,函数,参数,递归,作用域
- 《Python基础教程》读书笔记(2)之第7章更加抽象(关键词:Python/面向对象/多态/封装/方法/继承)
- 《Python基础教程》读书笔记(4)之第9章魔法方法、属性和迭代器(关键词:Python/魔法方法/属性/迭代器)
- 《Python基础教程》 读书笔记 第六章 抽象 函数 参数
- 《Python学习手册》学习笔记(18)之第18章参数(关键词:编程语言/Python/参数)
- python参数关键词使用
- 《Python语言及其应用》读书笔记(2)之第3章Python容器:列表、元组、字典与集合(关键词:列表/元组/字典/集合)
- 《Python基础教程》学习笔记之[D7]抽象之函数定义,参数(一)
- C# 语言在函数参数列表中出现this关键词的作用
- Python基础教程 第6章: 抽象(函数) 学习笔记
- 《图解HTTP》读书笔记(6)第6章HTTP首部(关键词:HTTP/)
- python 第6章抽象
- python学习(十一)函数、作用域、参数
- 《数据结构与算法-Python语言描述》读书笔记(2)第2章抽象数据类型和Python类(关键词:数据结构/算法/Python/抽象数据类型/Python类)
- 《Python语言及其应用》读书笔记(5)之第6章对象和类(关键词:对象/类)
- python 第6章抽象
- 浅析Python中yield关键词的作用与用法
- python 作用域与带有循环变量的默认参数比较
- C# 语言在函数参数列表中出现this关键词的作用