变量由作用范围限制
分类
变量的作用范围:
LEGB原则:
globals 函数和 locals 函数(内建函数)
eval()函数
eval(string_code, globals=None, locals=None)
x = 10
y = 20
# 执行x+y
# z = x + y
z1 = x + y
z2 = eval("x+y")
print(z1)
print(z2)
# result:
30
30
x = 10
y = 20
# 执行x+y
# z = x + y
z1 = x + y
z2 = exec("x+y")
print(z1)
print(z2)
# result:
30
None
函数直接或者间接调用自身
优点:简洁,易理解
缺点:对递归的深度有限制,消耗资源大
python对递归深度有限制,超过限制会报错
在写递归程序的时候,一定要注意边界条件
斐波那契数列(Fibonacci sequence),又称黄金分割数列、因数学家列昂纳多·斐波那契(Leonardoda Fibonacci)以兔子繁殖为例子
而引入,故又称为“兔子数列”,指的是这样一个数列:1、1、2、3、5、8、13、21、34、……在数学上,斐波纳契数列以如下被以递推
的方法定义:F(1)=1,F(2)=1, F(n)=F(n-1)+F(n-2)(n>=3,n∈N*)
# n表示求第n个数字的斐波那契数列的值
def fib(n):
if n == 1:
return 1
if n == 2:
return 1
# 思考为什么后面return能够正确执行,而不用else语句
return fib(n-1) + fib(n-2)
print(fib(3))
print(fib(10))
# result:
2
55
汉诺塔规则:
1.每次只能移动一个盘子
2.任何一次移动,三个塔的状态必须是小盘子在上,大盘子在下
def hano(n, a, b, c):
'''
汉诺塔的递归实现:
n:代表盘子的个数
a:代表第一个塔(初始)
b:代表第二个塔(过渡)
c:代表第三个塔(目标塔)
'''
if n == 1:
print(a, "-->", c)
return None
# 把n-1个盘子,从a塔借助c塔,移动到b塔上
hano(n - 1, a, c, b)
print(a, "-->", c)
# 把n-1个盘子,从b塔借助a塔,移动到c塔上
hano(n - 1, b, a, c)
a = "A"
b = "B"
c = "C"
hano(3, a, b, c)
A --> C
A --> B
C --> B
A --> C
B --> A
B --> C
A --> C
序列是Python中最基本的数据结构。序列中的每个元素都分配一个数字 - 它的位置,或索引,第一个索引是0,第二个索引是1,依此类推。
Python有6个序列的内置类型,但最常见的是列表和元组。
序列都可以进行的操作包括索引,切片,加,乘,检查成员
列表的数据项不需要具有相同的类型
创建列表逗号分隔的不同的数据项使用方括号括起来即可
创建列表:
# 创建空列表
l1 = []
# type是内置函数,负责打印出变量的类型
print(type(l1))
# 创建带值的列表
l2 = [100]
print(type(l2))
print(l2)
# 创建一个带多值的列表
l3 = [2,3,4,5,6]
print(type(l3))
print(l3)
# 使用 list() 函数
l4 = list()
print(type(l4))
print(l4)
# 下标访问列表
lst = [9,6,3,2,1]
print(l[2])
3
#切片操作
#注意截取的范围,包含左边的下标值,不包含右边的下标值
lst = [9,6,3,2,1]
print(lst[1:3])
print(lst[:])
print(lst[:4])
print(lst[2:])
# 切片可以控制增长的幅度(步长)
# 下标可以超出范围,但超出后不考虑余下内容
# 最后一个数字的下标为 -1
# 切片默认从左往右
# 正常情况下,切片左边的值一定小于右边的值
# 如果切片左边值大于右边值,步长参数需要使用负数
print("1-",lst[-4:-2])
print("2-",lst[-2:-4])
# result:
[6, 3]
[9, 6, 3, 2, 1]
[9, 6, 3, 2]
[3, 2, 1]
1- [6, 3]
2- []
# 通过id判断出切片是新生成了一个list还是同一个list
lst = [1,5,2,4,7,89,123]
lst_1 = lst[:]
lst_2 = lst_1
print(id(lst))
print(id(lst_1))
print(id(lst_2))
# result:
2091311194632
2091311194696
2091311194696
# del 删除
lst = [1,2,3,4,5,6]
del lst[2]
print(lst)
# result:
[1,2,4,5,6]
lst = [1,2,3,4,5,6]
print(lst)
print(id(lst))
del lst[2]
print(lst)
print(id(lst))
# result:
[1, 2, 3, 4, 5, 6]
2429626573320
[1, 2, 4, 5, 6]
2429626573320
lst_a = [1,2,3]
lst_b = [4,5,6]
lst_c = ["a","b","c"]
lst = lst_a + lst_b + lst_c
print(lst)
# result:
[1, 2, 3, 4, 5, 6, 'a', 'b', 'c']
# 列表直接跟一个整数相乘
# 相当于把n个列表接在一起
lst = [1,2,3]
lst_a = lst * 3
print(lst)
print(lst_a)
# result:
[1, 2, 3]
[1, 2, 3, 1, 2, 3, 1, 2, 3]
# 即判断一个元素是否在list中
lst = [1,2,3]
a = 3
# 返回的是一个布尔值
b = a in lst
print(b)
# result:
True
# for * in list
# in 后的变量应是可迭代对象
lst = [1,2,3,4,5]
for i in lst:
print(i)
# result:
1
2
3
4
5
# 此种用法可以过滤原来列表并放入新列表
a = [1,2,3,4,5]
b =[i*10 for i in a]
print(b)
# 将列表lst中的偶数放入lst_a
lst = [i for i in range(1,11)]
lst_a =[j for j in lst if j % 2 == 0]
print(lst_a)
# 列表生成式可以嵌套
# 生成两个列表lst_1和lst_2
lst_1 = [i for i in range(1,4)]
print(lst_1)
lst_2 = [j for j in range(1,400) if j % 100 == 0]
print(lst_2)
# 其实相当于两个for循环嵌套,但示例生成的是列表
lst_3 = [m+n for m in lst_1 for n in lst_2]
print(lst_3)
# 上下大致等价
for m in lst_a:
for n in lst_b:
print(m+n,end=" ")
print()
# result:
[10, 20, 30, 40, 50]
[2, 4, 6, 8, 10]
[1, 2, 3]
[100, 200, 300]
[101, 201, 301, 102, 202, 302, 103, 203, 303]
101 201 301 102 202 302 103 203 303
# len() :求列表的长度
lst = [i for i in range(1,50)]
print(len(lst))
# max() :求列表中元素的最大值
# min() :求列表中元素的最小值
print (max(lst))
print (min(lst))
# list() :将其他格式的数据转换为lsit类型
str = "ni hao ya ,jing ke ai!"
lst = list(str)
print(lst)
# 把range()产生的内容转换为lsit
print(list(range(1,99)))
49
49
1
['n', 'i', ' ', 'h', 'a', 'o', ' ', 'y', 'a', ',', 'J', 'i', 'n', 'g', ' ', 'k', 'e', ' ', 'a', 'i', '!']
[1, 2, 3, 4]
集合(set)是一个无序的不重复元素序列。
可以使用大括号 { } 或者 set() 函数创建集合,注意:创建一个空集合必须用 set() 而不是 { },因为 { } 是用来创建一个空字典。
创建格式:
parame = {v1,v2,3,........}
#或者
set(v1,v2,v3,........)
#集合具有自动去重功能
#集合具有自动去重功能
basket = {'apple', 'orange', 'pear', 'orange', 'banana'}
print(basket)
#集合的成员判断
print('orange' in basket)
print('hello' in basket)
#集合间的运算
set_a = set('abcdefg')
set_b = set('efghij')
print(set_a)
print(set_a - set_b) # 集合set_a中包含而集合set_b中不包含的元素
print(set_a | set_b) # 集合set_a或set_b中包含的所有元素
print(set_a & set_b) # 集合set_a和set_b中都包含了的元素
print(set_a ^ set_b) # 不同时包含于set_a和set_b的元素
#result:
{'orange', 'pear', 'apple', 'banana'}
True
False
{'a', 'e', 'g', 'f', 'd', 'b', 'c'}
{'a', 'c', 'd', 'b'}
{'a', 'e', 'i', 'g', 'f', 'h', 'd', 'b', 'c', 'j'}
{'g', 'f', 'e'}
{'a', 'i', 'h', 'd', 'b', 'c', 'j'}
set_a = {i for i in 'abcdefg' if i not in 'efg'}
print(set_a)
#result:
{'c', 'a', 'b', 'd'}
#向集合中添加元素
a = {'apple','orange'}
print(a)
a.add('jingkeai')
print(a)
#set.update()也可以向集合添加元素(参数可以是列表,元组,字典等)
a = {'apple','orange'}
a.update({'a','b','c'})
print(a)
a.update([1,2,3],['J','K','A'])
print(a)
#删除集合中的元素
a.remove(1) #remove只能有一个参数(只能删除一个元素),如果元素不存在,则会报错
print(a)
a.discard(1) #此方法删除集合中的元素,如果元素不存在,不会报错。
print(a)
#随机删除集合中的一个元素
a.pop()
print(a) #这里每次输出的结果都可能不一致,因为pop对集合中的元素是随机弹出的
#统计集合中元素的个数
print(len(a))
#清空集合
a.clear()
print(a)
{'orange', 'apple'}
{'orange', 'jingkeai', 'apple'}
{'orange', 'b', 'apple', 'a', 'c'}
{1, 2, 3, 'J', 'c', 'b', 'a', 'orange', 'A', 'apple', 'K'}
{2, 3, 'J', 'c', 'b', 'a', 'orange', 'A', 'apple', 'K'}
{2, 3, 'J', 'c', 'b', 'a', 'orange', 'A', 'apple', 'K'}
{3, 'J', 'c', 'b', 'a', 'orange', 'A', 'apple', 'K'}
9
set()
字典是另一种可变容器模型,且可存储任意类型对象。
字典的每个键值(key=>value)对用冒号(:)分割,每个对之间用逗号(,)分割,整个字典包括在花括号({})中
格式:d = {key1 : value1, key2 : value2 …}
键必须是唯一的,值不必唯一
值可以是任何数据类型,键必须是不可变的(如字符串、数字、元组)
字典创建实例:
#字典创建
dict_a = {'xuhaoxuan':20,'lijingyi':'19','datouerzi':'???'}
dict_b = {'1':'a',(1):3}
for k,v in dict_a.items():
print(k,'->',v)
for k,v in dict_b.items():
print(k,'->',v)
#访问字典的值
print("dict_a['xuhaoxuan']",dict_a['xuhaoxuan'])
print("dict_b['1']",dict_b['1']) #如果访问字典里没有的键,则会报错keyError
#修改字典的值
dict_a['lijingyi'] = 'shazhu'
print("dict_a['lijingyi']",dict_a['lijingyi'])
#删除字典的元素
del dict_a['xuhaoxuan']
print(dict_a)
#清空字典
dict_a.clear()
print(dict_a)
#删除字典
del dict_a
# 字典的内置函数和方法
a = {'name':'xuhaoxuan','age':20,'class':2}
print(str(a))
print(type(str(a))) #输出字典,用可打印的字符串表示
print(len(a)) #统计字典中键的个数
xuhaoxuan -> 20
lijingyi -> 19
datouerzi -> ???
1 -> a
1 -> 3
dict_a['xuhaoxuan'] 20
dict_b['1'] a
dict_a['lijingyi'] shazhu
{'lijingyi': 'shazhu', 'datouerzi': '???'}
{}
{'name': 'xuhaoxuan', 'age': 20, 'class': 2}
<class 'str'>
3
Python 的元组与列表类似,不同之处在于元组的元素不能修改。
元组使用小括号,列表使用方括号。
元组创建很简单,只需要在括号中添加元素,并使用逗号隔开即可。
# 创建空元组
tup1 = (1,2,3,4)
print(tup1)
tup2 = ('xuhaoxuan',20)
print(tup2)
# 创建元组也可以不用括号
tup3 = 'xuhaoxuan','xieiqngsong',20,19
print(tup3)
# 特别注意,当元组中只有一个元素时,必须在该元素后面加逗号,否则括号会被当做运算符
tup1 = (1)
print(type(tup1)) # 此时是整型数据
tup1 = (1,)
print(type(tup1)) # 此时是元组
# 元组可以通过索引访问元素
print(tup3[1])
print(tup3[2:4]) # 右边界同样不包含
# 元组的元素不能进行修改,但是可以进行连接
tup_a = tup3 + tup2
print(tup_a) # 两个'xuhaoxuan'都被元组保存,说明元组的值是可以重复的
# 元组的值不能被删除,但可以直接删除整个元组
del tup_a
# 元组可迭代
# tuple()函数可以将列表转换为元组
#result:
(1, 2, 3, 4)
('xuhaoxuan', 20)
('xuhaoxuan', 'xieiqngsong', 20, 19)
<class 'int'>
<class 'tuple'>
xieiqngsong
(20, 19)
('xuhaoxuan', 'xieiqngsong', 20, 19, 'xuhaoxuan', 20)