教程:用Python和Sage编程¶
本教程将介绍Python和Sage中的基本编程,读者将了解编程的基本概念,但不熟悉Python语言。它远不是详尽无遗的。有关更完整的教程,请查看 Python Tutorial . 也是Python的 documentation 尤其是 standard library 可能有用。
A more advanced tutorial 介绍Python中对象和类的概念。
下面是学习Python的更多资源:
Learn Python in 10 minutes ou en français Python en 10 minutes
Dive into Python 是一本面向有经验的程序员的Python书。也可在 other languages .
Discover Python 是在IBM的 developerWorks 技术资源中心。
数据结构¶
在 Python 中, 打字是动态的 不存在声明变量的事情。功能 type()
返回对象的类型 obj
. 将对象转换为类型 typ
就写吧 typ(obj)
如在 int("123")
. 命令 isinstance(ex, typ)
返回表达式是否 ex
属于类型 typ
. 具体来说,任何值都是 类的实例 类和类型之间没有区别。
符号 =
表示对变量的矫饰;不应与 ==
表示数学上的相等。不平等是 !=
.
这个 标准类型 是 bool
, int
, list
, tuple
, set
, dict
, str
.
类型
bool
( 布尔运算 )有两个值:True
和False
. 布尔运算符由它们的名称表示or
,and
,not
.Python类型
int
和long
用于表示有限大小的整数。Sage使用自己的类型名为Integer
.A list 是对值进行分组的数据结构。它是使用括号构造的,如中所示
[1, 3, 4]
. 这个range()
函数创建整数列表。也可以使用 列表理解 :[ <expr> for <name> in <iterable> (if <condition>) ]
例如::
sage: [ i^2 for i in range(10) if i % 2 == 0 ] [0, 4, 16, 36, 64]
A 元组 非常类似于列表;它是用括号构造的。空元组通过
()
或由建造师tuple
. 如果只有一个元素,就必须写(a,)
. 元组是 不变的 (一个人无法改变它)但是它是 可装卸的 (见下文)。也可以使用理解来创建元组:sage: tuple(i^2 for i in range(10) if i % 2 == 0) (0, 4, 16, 36, 64)
A set 是一种数据结构,它包含没有重数或顺序的值。可以使用构造函数从列表(或任何iterable)中创建它
set
. 集合的元素必须是散列的:sage: set([2,2,1,4,5]) {1, 2, 4, 5} sage: set([ [1], [2] ]) Traceback (most recent call last): ... TypeError: unhashable type: 'list'
A 词典 是一个关联表,它将值与键相关联。密钥必须是散列的。使用构造函数创建字典
dict
,或使用以下语法:{key1 : value1, key2 : value2 ...}
例如::
sage: age = {'toto' : 8, 'mom' : 27}; age {'mom': 27, 'toto': 8}
引号(简单
' '
或者双倍" "
)封闭 字符串 . 可以使用+
.对于列表、元组、字符串和字典 索引运算符 是书面的
l[i]
. 对于列表、元组和字符串,也可以使用 片 作为l[:]
,l[:b]
,l[a:]
或l[a:b]
. 负指数从末尾开始。这个
len()
函数返回列表、元组、集、字符串或字典的元素数。有人写道x in C
测试x
是在C
.最后还有一个特殊的值叫做
None
表示没有值。
控制结构¶
在Python中,指令块的开头和结尾没有关键字。块仅通过缩进来分隔。在大多数情况下,新块是由 :
. Python具有以下控制结构:
条件指令:
if <condition>: <instruction sequence> [elif <condition>: <instruction sequence>]* [else: <instruction sequence>]
在表达式内部,可以写下:
<value> if <condition> else <value>
迭代指令:
for <name> in <iterable>: <instruction sequence> [else: <instruction sequence>]
while <condition>: <instruction sequence> [else: <instruction sequence>]
这个
else
块在循环结束时执行,如果循环正常结束,则break
也不例外。在一个循环中,
continue
跳到下一个迭代。iterable是一个可以迭代的对象。Iterable类型包括列表、元组、字典和字符串。
错误(也称为异常)由以下原因引发:
raise <ErrorType> [, error message]
常见错误包括
ValueError
和TypeError
.
功能¶
注解
Python函数与数学函数
在接下来的内容中,我们处理 功能 是什么意思 程序设计语言 . 在微积分中,数学函数是由Sage以不同的方式处理的。尤其是在Python函数上进行数学操作(如添加或派生)是没有意义的。
使用关键字定义函数 def
AS:
def <name>(<argument list>):
<instruction sequence>
函数的结果由指令给出 return
. 可以使用匿名方式创建非常短的函数 lambda
(注意没有指示 return
在这里):
lambda <arguments>: <expression>
练习¶
列表¶
创建列表I: [方括号]¶
例子:
sage: L = [3, Permutation([5,1,4,2,3]), 17, 17, 3, 51]
sage: L
[3, [5, 1, 4, 2, 3], 17, 17, 3, 51]
练习: 创建列表 [63, 12, -10, "a", 12]
,将其分配给变量 L
,并打印列表。
sage: # edit here
练习: 创建空列表(通常需要这样做)。
sage: # edit here
创建列表II:范围¶
这个 range()
函数提供了构造整数列表的简单方法。以下是 range()
功能:
range([start,] stop[, step]) -> list of integers
Return a list containing an arithmetic progression of integers.
range(i, j) returns [i, i+1, i+2, ..., j-1]; start (!) defaults to 0.
When step is given, it specifies the increment (or decrement). For
example, range(4) returns [0, 1, 2, 3]. The end point is omitted!
These are exactly the valid indices for a list of 4 elements.
练习: 使用 range()
构建列表 [1,2,ldots,50] .
sage: # edit here
练习: 使用 range()
构建 even 1到100之间的数字(包括100)。
sage: # edit here
练习: 这个 step
的参数 range()
命令可以是负数。使用范围构造列表 [10, 7, 4, 1, -2] .
sage: # edit here
参见
xrange()
:返回迭代器而不是构建列表(仅适用于Python2,在python3中被range替换)。srange()
:与范围相似,但带有Sage整数;见下文。xsrange()
:与xrange相似,但带有Sage整数。
创建列表III:列表理解¶
列表解析 提供从其他列表(或其他数据类型)创建列表的简明方法。
例子 我们已经知道如何创建列表 [1, 2, dots, 16] ::
sage: range(1,17) # py2
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16]
使用A 列表理解 ,我们现在可以创建列表 [1^2, 2^2, 3^2, dots, 16^2] 如下:
sage: [i^2 for i in range(1,17)]
[1, 4, 9, 16, 25, 36, 49, 64, 81, 100, 121, 144, 169, 196, 225, 256]
sage: sum([i^2 for i in range(1,17)])
1496
Exercise: [Project Euler, Problem 6]
前十个自然数的平方和为
前十个自然数之和的平方是
因此,前十个自然数的平方和和与之和的平方之差为
找出前一百个自然数的平方和和和的平方的差。
sage: # edit here
sage: # edit here
sage: # edit here
使用列表理解过滤列表¶
列表可以是 过滤的 使用列表理解。
例子: 要创建1到100之间的素数平方的列表,我们使用如下列表理解。
sage: [p^2 for p in [1,2,..,100] if is_prime(p)]
[4, 9, 25, 49, 121, 169, 289, 361, 529, 841, 961, 1369, 1681, 1849, 2209, 2809, 3481, 3721, 4489, 5041, 5329, 6241, 6889, 7921, 9409]
练习: 使用A 列表理解 列出20以下所有3或5的倍数的自然数。提示:
要得到7除以3的余数,请使用
7%3
.用两个等号来检验相等性 (
==
);例如,3 == 7
.
sage: # edit here
Project Euler, Problem 1: 求1000以下所有3或5的倍数之和。
sage: # edit here
嵌套列表理解¶
列表理解可以嵌套!
例子:
sage: [(x,y) for x in range(5) for y in range(3)]
[(0, 0), (0, 1), (0, 2), (1, 0), (1, 1), (1, 2), (2, 0), (2, 1), (2, 2), (3, 0), (3, 1), (3, 2), (4, 0), (4, 1), (4, 2)]
sage: [[i^j for j in range(1,4)] for i in range(6)]
[[0, 0, 0], [1, 1, 1], [2, 4, 8], [3, 9, 27], [4, 16, 64], [5, 25, 125]]
sage: matrix([[i^j for j in range(1,4)] for i in range(6)])
[ 0 0 0]
[ 1 1 1]
[ 2 4 8]
[ 3 9 27]
[ 4 16 64]
[ 5 25 125]
练习:
A 三重勾股 是三倍的 (x,y,z) 属于 积极的 满足整数 x^2+y^2=z^2 . 毕达哥拉斯的三元组,其组分最多 10 是:
\[[(3,4,5),(4,3,5),(6,8,10),(8,6,10)] ,.\]使用过滤的列表理解,构造一个包含最多个组件的毕达哥拉斯三元组的列表 50 ::
sage: # edit here
sage: # edit here
Project Euler, Problem 9: 只有一个毕达哥拉斯式的三元组 a + b + c = 1000 . 找到产品 abc ::
sage: # edit here
访问列表的单个元素¶
访问列表中的元素 L
,使用语法 L[i]
在哪里 i 是项的索引。
练习:
构建列表
L = [1,2,3,4,3,5,6]
. 是什么L[3]
是吗?sage: # edit here
是什么
L[1]
是吗?sage: # edit here
的第一个元素的索引是什么
L
是吗?sage: # edit here
是什么
L[-1]
? 是什么L[-2]
是吗?sage: # edit here
是什么
L.index(2)
? 是什么L.index(3)
是吗?sage: # edit here
修改列表:更改列表中的元素¶
更改项目位置 i
列表的 L
::
sage: L = ["a", 4, 1, 8]
sage: L
['a', 4, 1, 8]
sage: L[2] = 0
sage: L
['a', 4, 0, 8]
修改列表:附加和扩展¶
到 追加 列表的对象:
sage: L = ["a", 4, 1, 8]
sage: L
['a', 4, 1, 8]
sage: L.append(17)
sage: L
['a', 4, 1, 8, 17]
到 延伸 另一个列表的列表:
sage: L1 = [1,2,3]
sage: L2 = [7,8,9,0]
sage: L1
[1, 2, 3]
sage: L2
[7, 8, 9, 0]
sage: L1.extend(L2)
sage: L1
[1, 2, 3, 7, 8, 9, 0]
修改列表:反转、排序。。。¶
sage: L = [4,2,5,1,3]
sage: L
[4, 2, 5, 1, 3]
sage: L.reverse()
sage: L
[3, 1, 5, 2, 4]
sage: L.sort()
sage: L
[1, 2, 3, 4, 5]
sage: L = [3,1,6,4]
sage: sorted(L)
[1, 3, 4, 6]
sage: L
[3, 1, 6, 4]
连接列表¶
若要连接两个列表,请使用运算符将它们相加 +
. 这不是交换操作!
sage: L1 = [1,2,3]
sage: L2 = [7,8,9,0]
sage: L1 + L2
[1, 2, 3, 7, 8, 9, 0]
切片列表¶
可以使用以下语法对列表进行切片 L[start : stop : step]
. 这将返回 L
.
练习: 下面是一些切片列表的示例。在计算单元格之前,请尝试猜测输出结果:
sage: L = list(range(20))
sage: L
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19]
sage: L[3:15]
[3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14]
sage: L[3:15:2]
[3, 5, 7, 9, 11, 13]
sage: L[15:3:-1]
[15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4]
sage: L[:4]
[0, 1, 2, 3]
sage: L[:]
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19]
sage: L[::-1]
[19, 18, 17, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0]
练习(高级): 下面的函数将循环与上面的一些列表操作组合在一起。函数的作用是什么?
sage: def f(number_of_iterations):
....: L = [1]
....: for n in range(2, number_of_iterations):
....: L = [sum(L[:i]) for i in range(n-1, -1, -1)]
....: return numerical_approx(2*L[0]*len(L)/sum(L), digits=50)
sage: # edit here
多元组¶
A 元组 是一个 不变的 列表。也就是说,它一旦创建就不能更改。这对于代码安全非常有用,最重要的原因是它生成元组 可装卸的 . 要创建元组,请使用括号而不是括号::
sage: t = (3, 5, [3,1], (17,[2,3],17), 4)
sage: t
(3, 5, [3, 1], (17, [2, 3], 17), 4)
要创建单例元组,需要使用逗号来解决歧义:
sage: (1)
1
sage: (1,)
(1,)
我们可以从列表创建元组,反之亦然。
sage: tuple(range(5))
(0, 1, 2, 3, 4)
sage: list(t)
[3, 5, [3, 1], (17, [2, 3], 17), 4]
元组在许多方面类似于列表:
操作 |
列表的语法 |
元组的语法 |
---|---|---|
查阅信件 |
|
|
级联 |
|
|
切片 |
|
|
颠倒的副本 |
|
|
长度 |
|
|
尝试修改元组将失败::
sage: t = (5, 'a', 6/5)
sage: t
(5, 'a', 6/5)
sage: t[1] = 'b'
Traceback (most recent call last):
...
TypeError: 'tuple' object does not support item assignment
生成器¶
“元组理解”并不存在。相反,语法生成了一个称为生成器的东西。生成器允许您一次处理一个项目序列。每一项都是在需要时创建的,然后被遗忘。如果我们只需要使用每件物品一次,这会非常有效。
sage: (i^2 for i in range(5))
<generator object <genexpr> at 0x...>
sage: g = (i^2 for i in range(5))
sage: g[0]
Traceback (most recent call last):
...
TypeError: 'generator' object ...
sage: [x for x in g]
[0, 1, 4, 9, 16]
g
现在是空的。
sage: [x for x in g]
[]
一个不错的“pythonic”技巧是使用生成器作为函数的参数。我们有 not 需要双括号:
sage: sum( i^2 for i in srange(100001) )
333338333350000
辞典¶
A 词典 是另一种内置数据类型。与列表不同,列表是按从0开始的一系列数字编制索引的,字典的索引依据 keys ,可以是任何不可变的对象。字符串和数字总是可以是键(因为它们是不可变的)。字典有时在其他编程语言中被称为“关联数组”。
定义字典有几种方法。一种方法是用大括号, {{}}
,表格中给出了逗号分隔的条目 键:值 ::
sage: d = {3:17, 0.5:[4,1,5,2,3], 0:"goo", 3/2 : 17}
sage: d
{0: 'goo', 0.500000000000000: [4, 1, 5, 2, 3], 3/2: 17, 3: 17}
第二种方法是使用构造函数 dict
它允许一个2元组的列表(或者实际上是任何iterable) 值(键) ::
sage: dd = dict((i,i^2) for i in range(10))
sage: dd
{0: 0, 1: 1, 2: 4, 3: 9, 4: 16, 5: 25, 6: 36, 7: 49, 8: 64, 9: 81}
对于一些重要的字典和操作,元组和操作都是重要的。
操作 |
列表的语法 |
词典语法 |
---|---|---|
访问元素 |
|
|
长度 |
|
|
修改 |
|
|
删除项目 |
|
|
sage: d[10]='a'
sage: d
{0: 'goo', 0.500000000000000: [4, 1, 5, 2, 3], 3/2: 17, 3: 17, 10: 'a'}
一个字典可以多次具有相同的值,但每个键只能出现一次并且必须是不可变的:
sage: d = {3: 14, 4: 14}
sage: d
{3: 14, 4: 14}
sage: d = {3: 13, 3: 14}
sage: d
{3: 14}
sage: d = {[1,2,3] : 12}
Traceback (most recent call last):
...
TypeError: unhashable type: 'list'
另一种向字典中添加项目的方法是使用 update()
从另一个词典更新词典的方法::
sage: d = {}
sage: d
{}
sage: d.update({10 : 'newvalue', 20: 'newervalue', 3: 14, 0.5:[1,2,3]})
sage: d
{0.500000000000000: [1, 2, 3], 3: 14, 10: 'newvalue', 20: 'newervalue'}
我们可以迭代 keys 或 价值观 或两者兼而有之。注意,在内部,没有对键进行排序。一般来说,键/值的顺序取决于不同计算机和/或在同一台计算机上重复运行的内存位置的不同。但是,Sage在打印字典时按键对字典条目进行排序,以使docstring更具可复制性。但是,Python方法 keys()
和 values()
不要为你分类。如果你想要你的输出是可复制的,那么你必须像下面的例子一样先对它排序:
sage: d = {10 : 'newvalue', 20: 'newervalue', 3: 14, 0.5:(1,2,3)}
sage: sorted([key for key in d])
[0.500000000000000, 3, 10, 20]
sage: d.keys() # random order
[0.500000000000000, 10, 3, 20]
sage: sorted(d.keys())
[0.500000000000000, 3, 10, 20]
sage: d.values() # random order
[(1, 2, 3), 'newvalue', 14, 'newervalue']
sage: set(d.values()) == set([14, (1, 2, 3), 'newvalue', 'newervalue'])
True
sage: d.items() # random order
[(0.500000000000000, (1, 2, 3)), (10, 'newvalue'), (3, 14), (20, 'newervalue')]
sage: sorted([(key, value) for key, value in d.items()])
[(0.500000000000000, (1, 2, 3)), (3, 14), (10, 'newvalue'), (20, 'newervalue')]
练习: 考虑下面的有向图。

创建一个字典,其键是上述有向图的顶点,其值是它指向的顶点列表。例如,顶点1指向顶点2和3,因此字典将如下所示:
d = { ..., 1:[2,3], ... }
sage: # edit here
然后尝试:
sage: g = DiGraph(d)
sage: g.plot()
使用Sage类型:srange命令¶
例子: 构建一个 3 times 3 谁的矩阵 (i,j) 入口是有理数 frac{{i}}{{j}} . 由生成的整数 range()
是 Python 吗 int
因此,对它们进行欧几里德除法(在 Python 2中)::
sage: matrix([[i/j for j in range(1,4)] for i in range(1,4)]) # not tested
[1 0 0]
[2 1 0]
[3 1 1]
在Python3中,Python整数的除法返回一个float。
而将Sage分开 Integer
一位Sage Integer
产生一个有理数:
sage: matrix([[ i/j for j in srange(1,4)] for i in srange(1,4)])
[ 1 1/2 1/3]
[ 2 1 2/3]
[ 3 3/2 1]
修改列表会有后果!¶
尝试预测以下命令的结果:
sage: a = [1, 2, 3]
sage: L = [a, a, a]
sage: L
[[1, 2, 3], [1, 2, 3], [1, 2, 3]]
sage: a.append(4)
sage: L
[[1, 2, 3, 4], [1, 2, 3, 4], [1, 2, 3, 4]]
现在试试这些:
sage: a = [1, 2, 3]
sage: L = [a, a, a]
sage: L
[[1, 2, 3], [1, 2, 3], [1, 2, 3]]
sage: a = [1, 2, 3, 4]
sage: L
[[1, 2, 3], [1, 2, 3], [1, 2, 3]]
sage: L[0].append(4)
sage: L
[[1, 2, 3, 4], [1, 2, 3, 4], [1, 2, 3, 4]]
这被称为 参考效应 . 您可以使用命令 deepcopy()
为了避免这种影响:
sage: a = [1,2,3]
sage: L = [deepcopy(a), deepcopy(a)]
sage: L
[[1, 2, 3], [1, 2, 3]]
sage: a.append(4)
sage: L
[[1, 2, 3], [1, 2, 3]]
字典也有同样的效果:
sage: d = {1:'a', 2:'b', 3:'c'}
sage: dd = d
sage: d.update( { 4:'d' } )
sage: dd
{1: 'a', 2: 'b', 3: 'c', 4: 'd'}
循环和函数¶
对于这里所发生的事情的更详细的解释,下面是Python教程的一个好地方:http://docs.python.org/tutorial/controlflow.html
同时 循环¶
同时 循环的使用量往往不如 for Python代码中的循环:
sage: i = 0
sage: while i < 10:
....: print(i)
....: i += 1
0
1
2
3
4
5
6
7
8
9
sage: i = 0
sage: while i < 10:
....: if i % 2 == 1:
....: i += 1
....: continue
....: print(i)
....: i += 1
0
2
4
6
8
注意,中子句表达式的真值 虽然 循环使用 bool
::
sage: bool(True)
True
sage: bool('a')
True
sage: bool(1)
True
sage: bool(0)
False
sage: i = 4
sage: while i:
....: print(i)
....: i -= 1
4
3
2
1
For 循环¶
这是一个基本的 for 循环遍历列表中的所有元素 l
::
sage: l = ['a', 'b', 'c']
sage: for letter in l:
....: print(letter)
a
b
c
这个 range()
当您想要生成要循环的算术级数时,函数非常有用。请注意,不包括终点:
sage: range?
sage: range(4) # py2
[0, 1, 2, 3]
sage: range(1, 5) # py2
[1, 2, 3, 4]
sage: range(1, 11, 2) # py2
[1, 3, 5, 7, 9]
sage: range(10, 0, -1) # py2
[10, 9, 8, 7, 6, 5, 4, 3, 2, 1]
sage: for i in range(4):
....: print("{} {}".format(i, i*i))
0 0
1 1
2 4
3 9
你可以使用 持续 关键字以立即转到循环中的下一项:
sage: for i in range(10):
....: if i % 2 == 0:
....: continue
....: print(i)
1
3
5
7
9
如果要跳出循环,请使用 打破 关键词:
sage: for i in range(10):
....: if i % 2 == 0:
....: continue
....: if i == 7:
....: break
....: print(i)
1
3
5
如果您需要同时跟踪列表中的位置及其值,一种(不那么优雅)的方法是执行以下操作:
sage: l = ['a', 'b', 'c']
sage: for i in range(len(l)):
....: print("{} {}".format(i, l[i]))
0 a
1 b
2 c
用起来更干净 enumerate()
它提供了索引和值:
sage: l = ['a', 'b', 'c']
sage: for i, letter in enumerate(l):
....: print("{} {}".format(i, letter))
0 a
1 b
2 c
你可以得到与 enumerate()
使用函数 zip()
要将两个列表压缩在一起:
sage: l = ['a', 'b', 'c']
sage: for i, letter in zip(range(len(l)), l):
....: print("{} {}".format(i, letter))
0 a
1 b
2 c
For 循环使用Python的迭代器协议工作。这允许各种不同的对象循环。例如::
sage: for i in GF(5):
....: print("{} {}".format(i, i*i))
0 0
1 1
2 4
3 4
4 1
这是怎么回事?
sage: it = iter(GF(5)); it
<generator object ...__iter__ at 0x...>
sage: next(it)
0
sage: next(it)
1
sage: next(it)
2
sage: next(it)
3
sage: next(it)
4
sage: next(it)
Traceback (most recent call last):
...
StopIteration
sage: R = GF(5)
sage: R.__iter__??
命令 产量 提供了生成迭代器的非常方便的方法。我们稍后再看。
练习¶
对于以下每个集合,计算其元素的列表及其总和。如果可能的话,使用两种不同的方法:使用循环和使用列表理解。
第一 n 谐波级数项:
\[和{i=1}^nfrac{1}{i}\]sage: # edit here
之间的奇数 1 和 n ::
sage: # edit here
第一 n 奇数:
sage: # edit here
之间的整数 1 和 n 既不能被整除的 2 也不是 3 也不是 5 ::
sage: # edit here
第一 n 整数介于 1 和 n 既不能被整除的 2 也不是 3 也不是 5 ::
sage: # edit here
功能¶
函数是使用 def 语句,并使用 返回 关键词:
sage: def f(x):
....: return x*x
sage: f(2)
4
函数可以是递归的:
sage: def fib(n):
....: if n <= 1:
....: return 1
....: else:
....: return fib(n-1) + fib(n-2)
sage: [fib(i) for i in range(10)]
[1, 1, 2, 3, 5, 8, 13, 21, 34, 55]
函数和其他对象一样是一类对象。例如,它们可以作为参数传递给其他函数:
sage: f
<function f at 0x...>
sage: def compose(f, x, n): # computes f(f(...f(x)))
....: for i in range(n):
....: x = f(x) # this change is local to this function call!
....: return x
sage: compose(f, 2, 3)
256
sage: def add_one(x):
....: return x + 1
sage: compose(add_one, 2, 3)
5
可以为函数中的参数指定默认值:
sage: def add_n(x, n=1):
....: return x + n
sage: add_n(4)
5
sage: add_n(4, n=100)
104
sage: add_n(4, 1000)
1004
可以从函数中返回多个值::
sage: def g(x):
....: return x, x*x
sage: g(2)
(2, 4)
sage: type(g)
<... 'function'>
sage: a,b = g(100)
sage: a
100
sage: b
10000
您还可以在函数中获取可变数量的参数和关键字参数::
sage: def h(*args, **kwds):
....: print("{} {}".format(type(args), args))
....: print("{} {}".format(type(kwds), kwds))
sage: h(1,2,3,n=4)
<... 'tuple'> (1, 2, 3)
<... 'dict'> {'n': 4}
让我们使用 产量 指令为Fibonacci数到 n ::
sage: def fib_gen(n):
....: if n < 1:
....: return
....: a = b = 1
....: yield b
....: while b < n:
....: yield b
....: a, b = b, b+a
sage: for i in fib_gen(50):
....: print(i)
1
1
2
3
5
8
13
21
34
练习¶
编写函数
is_even
哪些回报True
如果n
是偶数和False
否则。编写函数
every_other
需要一张单子l
作为输入,并返回一个包含l
.编写生成器
every_other
这需要一个巨大的l
作为输入,并返回l
,一个接一个。编写一个函数来计算 n -斐波纳契数。努力提高表现。