仅用作个人学习记录
Reference:https://inst.eecs.berkeley.edu/~cs61a
Dictionaries
字典是键值对的可变映射。
>>> states = {
"CA": "California",
"DE": "Delaware",
"NY": "New York",
}
>>> len(states)
3
>>> "CA" in states
True
>>> "ZZ" in states
False
>>> states["CA"]
"California"
>>> states["AK"]
KeyError: AK
>>> states["AK"] = "Alaska"
>>> states
{"CA": "California", "DE": "Delaware", "NY": "New York", "AK" = "Alaska"}
>>> # Create an empty dict:
>>> uesr = {}
>>> # Add values:
>>> users["profpamela"] = "b3stp@ssEvErDontHackMe"
>>> # Change values:
>>> users["profpamela"] += "itsLongerSoItsMoreSecure!!"
>>> users["profpamela"]
'b3stp@ssEvErDontHackMeitsLongerSoItsMoreSecure!!'
>>> # 删除键 'profpamela'
>>> del uesr['profpamela']
>>> # 清空字典
>>> uesr.clear()
>>> # 删除字典
>>> del uesr
- 键必须不可变,键必须不可变类型,是可以用数字,字符串或元组充当,而用列表就不行。
- 不允许一个键出现两次。
insects = {"spiders": 8, "centipedes": 100, "bees": 6}
for name in insects:
print(insects[name])
8 100 6
字典是没有顺序的。Python 3新特性:键按照首次添加的顺序迭代。
Matrices
在前面,我们已经了解过嵌套数据:列表的列表、元组的列表等等。下面考虑如何使用嵌套数据抽象矩阵。
Implementation A
使用列表的列表、行主序:
[ [1,2,0,4], [0,1,3,-1], [0,0,1,8] ]
def matrix(rows, cols):
return [ [0 for col in range(cols)] for row in range(rows) ]
def value(matrix, row, col):
return matrix[row][col]
def set_value(matrix, row, col, val):
matrix[row][col] = val
m = matrix(3, 4)
set_value(m, 0, 0, 1)
set_value(m, 0, 1, 2)
set_value(m, 0, 3, 4)
Implementation B
使用列表的列表、列主序:
[ [1,0,0], [2,1,0], [0,3,1], [4,-1,8] ]
def matrix(rows, cols):
return [ [0 for row in range(rows)] for col in range(cols) ]
def value(matrix, row, col):
return matrix[col][row]
def set_value(matrix, row, col, val):
matrix[col][row] = val
m = matrix(3, 4)
set_value(m, 0, 0, 1)
set_value(m, 0, 1, 2)
set_value(m, 0, 3, 4)
Implementation C
使用列表的元组、行主序:
( [1,0,0], [2,1,0], [0,3,1], [4, -1,8] )
def matrix(rows, cols):
return tuple( [0 for col in range(cols)] for row in range(rows) )
def value(matrix, row, col):
return matrix[row][col]
def set_value(matrix, row, col, val):
matrix[row][col] = val
m = matrix(3, 4)
set_value(m, 0, 0, 1)
set_value(m, 0, 1, 2)
set_value(m, 0, 3, 4)
元组是不可变的,但是元组中的列表元素是对列表的引用,保存的是地址,即列表中的元素是可变的。
Implementation D
使用元素的列表、行主序:
[ (1,2,0,4), (0,1,3,-1), (0,0,1,8) ]
def matrix(rows, cols):
return [ tuple(0 for col in range(cols)) for row in range(rows) ]
def value(matrix, row, col):
return matrix[row][col]
def set_value(matrix, row, col, val):
matrix[row][col] = val
m = matrix(3, 4)
set_value(m, 0, 0, 1)
set_value(m, 0, 1, 2)
set_value(m, 0, 3, 4)
上述方案显然是不行的,元组是不可变的。
Implementation D2
改进:
def set_value(matrix, row, col, val):
matrix[row] = matrix[row][:col] + (val,) + matrix[row][col+1:]
方案可行但没必要。
Trees
Data abstraction
tree(label, children) :
Returns a tree with given LABEL at its root, whose children are CHILDREN
label(tree):
Returns the label of root node of TREE
children(tree):
Returns the children of TREE (each a tree)
is_leaf(tree):
Returns true if TREE is a leaf node.
Implementation A
[20, [12, [9, [7], [2]], [3]], [8, [4], [4]]]
def tree(label, children=[]):
return [label] + children
def label(tree):
return tree[0]
def children(tree):
return tree[1:]
def is_leaf(tree):
return len(children(tree)) == 0
t = tree(20, [tree(12,
[tree(9,
[tree(7), tree(2)]),
tree(3)]),
tree(8,
[tree(4), tree(4)])])
Implementation B
(20, [(12 , [(9, [(7, []), (2, [])]), (3, [])]), (8, [(4, []), (4, [])])])
def tree(label, children=[]):
return (label, children)
def label(tree):
return tree[0]
def children(tree):
return tree[1]
t = tree(20, [tree(12,
[tree(9,
[tree(7), tree(2)]),
tree(3)]),
tree(8,
[tree(4), tree(4)])])
Implementation C
{‘l’:20,‘c’:[{‘l’:12,‘c’:[{‘l’:9,‘c’:[{‘l’:7,‘c’: []},{‘l’:2,‘c’:[]}]},{‘l’:3,‘c’:[]}]}, {‘l’:8,‘c’:[{‘l’:4,‘c’:[]},{‘l’:4,‘c’:[]}]}]}
def tree(label, children=[]):
return {"l": label, "c": children}
def label(tree):
return tree["l"]
def children(tree):
return tree["c"]
t = tree(20, [tree(12,
[tree(9,
[tree(7), tree(2)]),
tree(3)]),
tree(8,
[tree(4), tree(4)])])
树是一种递归结构。每棵树都有一个标签、0个或多个孩子,孩子也是树。
Counting leaves
def count_leaves(t):
"""Returns the number of leaf nodes in T."""
if is_leaf(t):
return 1
else:
children_leaves = 0
for c in children(t):
children_leaves += count_leaves(c)
return children_leaves
def count_leaves(t):
"""Returns the number of leaf nodes in T."""
if is_leaf(t):
return 1
else:
return sum([count_leaves(c) for c in children(t)])