前言

  1. 在Python基础(一)中,非常感谢大家的点赞、收藏、评论、关注。
  2. 在Python基础(二)中,尽量用简洁易懂的方式来梳理知识点。
  3. 如果对你的学习有帮助,点个赞支持一下,一键三连哦~😄

Python基础(一): https://blog.csdn.net/weixin_46818279/article/details/108576298
 
 

7. 公共操作

 
什么是公共操作那???

公共操作:数据序列基本上都支持的一些操作
 

7.1 运算符

 

运算符描述支持的容器类型
+合并字符串、列表、元组
*复制字符串、列表、元组
in元素是否存在字符串、列表、元组、字典
not in元素是否存在字符串、列表、元组、字典

 
运算符:+(合并的作用)

str1 = 'aa'
str2 = 'bb'

list1 = [1,2]
list2 = [10,20]

t1 = (1,2)
t2 = (10,20)

dict1 = {'name':'tom'}
dict2 = {'age':30}

# 1. + : 合并
print(str1+str2)      # 输出 aabb
print(list1+list2)    # 输出 [1, 2, 10, 20]
print(t1+t2)          # 输出 (1, 2, 10, 20)
print(dict1+dict2)    # 报错:字典不支持合并运算

 
 
运算符:*(复制的作用)

str1 = 'a'
list = ['hello']
t1 = ('world',)

#   *:复制   支持字符串、列表、元组
print(str1 * 5)  # 输出aaaaa
print('-' * 10)  # 输出10个----------
print(list * 5)  # 输出['hello', 'hello', 'hello', 'hello', 'hello']
print(t1 * 5)    # 输出 ('world', 'world', 'world', 'world', 'world')

 
 
运算符:in、not in(判断元素是否存在)

str1 = 'abcd'
list1 = [10,20,30]
t1 = (100,200,300)
dict1 = {'name':'Python', 'age':30}
# in 和 not in

# 1. 字符a是否存在
print('a' in str1)  # 输出 True
print('a' not in str1)  # 输出 false

# 2. 数据10是否存在
print(10 in list1)   # 输出True
print(10 not in list1)  # 输出False

# 3. 100是否存在
print(100 in t1)    # 输出 True
print(100 not in t1)   # 输出Fasle

# 4. name是否存在
print(dict1)
print('name' in dict1)   # True
print('name' not in dict1)  # False
print('name' in dict1.keys()) # True
print('name' in dict1.values() ) # False

 
 

7.2 公共方法

公共方法之len()、del()、max()、min()、range(start,end,step)、enumerate()
这六个函数的作用以及用法,举栗子说明
 

(1)len():计算容器中元素的个数

str1 = 'abcd'
list1 = [10, 20, 30]
t1 = (100, 200, 300)
dict1 = {'name':'Python', 'age':30}
s1 = {10 , 20}

# len() 计算容器中元素个数
print(len(str1))  # 输出4
print(len(list1)) # 输出3
print(len(t1))    # 输出3
print(len(dict1)) # 输出2
print(len(s1))    # 输出2

 

(2)del():删除

str1 = 'abcd'
list1 = [10, 20, 30]
t1 = (100, 200, 300)
dict1 = {'name':'Python', 'age':30}
s1 = {10 , 20}

# 1. del 目标 或者 del(目标)

# str1字符串
del str1      # 删除整个字符串
print(str1)   # 报错说明已经删除成功

============================================================================
# list1 列表
del(list1)
print(list1) # 报错说明已经删除成功

# del(list1[0])
# print(list1)  # 输出[20, 30]

# del list1[0]
# print(list1)   # 输出[20, 30]

==============================================================================

# dict1 字典
del dict1
print(dict1) # 报错,已经删除成功
del dict1['name']
print(dict1)   #  输出结果为 {'age': 30}

==============================================================================

# s1 集合
del s1
print(s1) # 报错,已经删除成功




 
 
(3) max():返回容器中元素最大值
          min():返回容器中元素最小值

str1 = 'abcde'
list1 = [10, 20, 30]

# 1. max()最大值
print(max(str1))  # 输出e
print(max(list1))  # 输出30

# 2. min():最小值
print(min(str1))  # 输出a
print(min(list1)) # 输出10

 
 
(4)range():生成从start到end的数字,步长为step,供for循环使用

"""
注意事项:
    1. 如果不写开始,默认从0开始
    2. 如果不写步长,默认为1
"""

print(range(1,10,1)) # 输出 range(1, 10),返回的是可迭代的对象,需要配合for循环才能拿到数字
for i in range(1,10,1):
    # 遍历可迭代对象,并且拿到了对象内部的这些数字
    print(i)       # 输出的是1,2,3,4,5,6,7,8,9

for i in range(1,10):
    print(i)        # 如果不写步长,则默认步长是1

for i in range(1,10,2):
    print(i)       # 因为步长是2,所以输出1,3,5,7,9

for i in range(10):
    print(i)      # 这里的10代表结束。开始不写,默认从0开始。步长不写,默认为1。 但是不能不写结束!

 
 
(5)enumerate():函数用于将一个可遍历的数据对象(如列表、元组或字符串)组合为一个索引序列,同时列出数据和数据下标,一般用于在for循环当中。

# 1. 语法: enumerate(可遍历对象,start = 0)
# 2. start参数用来设置遍历数据的下标的起始值,默认为0

list1 = ['a', 'b', 'c', 'd', 'e']
# enumerate 返回结果是元组,元组第一个数据是原迭代对象的数据对应的下标,元组第二个数据是原迭代对象的数据
for i in enumerate(list1):
	print(i)
'''
输出的结果为:
(0, 'a')
(1, 'b')
(2, 'c')
(3, 'd')
(4, 'e')
'''

for i in enumerate(list1,start = 1):
    print(i)
'''
这时的start为1,输出的结果为:
(1, 'a')
(2, 'b')
(3, 'c')
(4, 'd')
(5, 'e')
'''

 

 

7.3 容器类型转换

 
直接上栗子:

# 已有的数据类型和程序想要的数据类型不一样,这个时候利用函数做类型的转换就可以了。

list1 = [10,20,30]
s1 = {100, 200, 300}
t1 = ('a', 'b', 'c')

# tuple():将某个序列转换成元组
print(tuple(list1))  # 输出结果为(10, 20, 30)
print(tuple(s1))    # 输出结果为(200, 100, 300)

# list():转换成列表
print(list(s1))      # 输出结果为 [200, 100, 300]
print(list(t1))     # 输出结果为 ['a', 'b', 'c']

# set():转换成集合
print(set(list1))   # 输出结果为{10, 20, 30}
print(set(t1))      # 输出结果为{'c', 'b', 'a'}

'''
注意:
    1. 集合可以快速完成列表去重
    2. 集合不支持下标(因为没有顺序)
'''

 
 

8. 推导式

 
推导式的作用:简化代码

列表推导式会返回一个列表 ,字典推导式会返回一个字典,集合推导式会返回一个集合
 
 

8.1 列表推导式

直接上代码:推导式如何简化代码的,如何使用推导式


'''
书写代码:
	1. 创建空列表
	2. 循环将有规律的数据写入到列表
	
方法实现:
	1. 循环实现 
	2. 列表推导式(化简代码,创建或控制有规律的列表)

得出结论:
	1. 列表推导式代码量最少,起到了简化代码的作用
'''
=========================================================================

# while 实现
list1 = []
i = 0
while i < 10:
    list1.append(i)
    i += 1
print(list1)  # 输出结果为[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

==========================================================================

# for 实现
# 用for实现比while实现所需的代码量少
list1 = []
for i in range(10):
    list1.append(i)
print(list1)   # 输出结果为[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

==========================================================================

# 列表推导式实现
list1 = [i for i in range(10)]  # 中括号里面第一个i,是接收数据的返回值,然后保存在列表中
print(list)    # 输出[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]


 

再举个栗子:带if的列表推导式

# 需求:0-10偶数数据的列表

# 1. 简单的列表推导式,range()步长实现
list1 = [i for i in range(0,10,2)]
print(list1)        # 输出结果为 [0, 2, 4, 6, 8]

# 2. for循环加if 创建有规律的列表
list2 = []
for i in range(10):
    if i % 2 == 0:
        list2.append(i)
print(list2)

# 3. 把for循环配合if的代码 改写 带if的列表推导式
list3 = [i for i in range(10) if i % 2 == 0]
print(list3)

 
 
再来个栗子:

'''
需求:创建列表如下:[(1,0),(1,1),(1,2),(2,0),(2,1),(2,2)]
1. 用for循环嵌套的方法进能够解决
    数据1:1 和 2 range(1,3)
    数据2:0 1 2 用 range(3)
2. 用列表推导式解决:多for的列表推导式等同于for循环嵌套,就是去掉标点、回车符和缩进。

'''

# 1. 用for循环嵌套

list1 = []
for i in range(1,3):
    for j in range(3):
        # 列表里面追加元素:循环前准备一个空列表,然后这里追加元组数据到列表
        list1.append((i,j))
print(list1)   # 输出结果为[(1, 0), (1, 1), (1, 2), (2, 0), (2, 1), (2, 2)]


# 2. 多个for实现列表推导式

list2 = [(i,j) for i in range(1,3) for j in range(3)]
print(list2)    # 输出结果为[(1, 0), (1, 1), (1, 2), (2, 0), (2, 1), (2, 2)]

经过上面这三个栗子,已经对推导式有一定的了解了,那么继续学习下面推导式的学习。
 
 

8.2 字典推导式

 
直接上栗子:

# 创建字典 key是1-4的数字,value是这个数字的平方
dict1 = {i: i**2 for i in range(1,5)}
print(dict1)  # 输出 {1: 1, 2: 4, 3: 9, 4: 16}

 

再举个栗子:合并列表为字典

# 1. 长度一样的列表合并字典
# list1 = ['name', 'age', 'gender']
# list2 = ['tom', 20, 'man']
# dict1 = {list1[i]: list2[i] for i in range(len(list1))}
# print(dict1)   # 输出的结果为 {'name': 'tom', 'age': 20, 'gender': 'man'}

# 长度不一样的列表合并成字典
list3 = ['name', 'age', 'gender', 'id']
list4 = ['tom', 20, 'man']

# 下面的语句会报错,因为不对等,如果取长的列表len(list3)则会报错
# dict1 = {list3[i]: list4[i] for i in range(len(list3))}

# 下面的语句才正确
dict2 = {list3[i]: list4[i] for i in range(len(list4))}
print(dict2)   # 输出结果为{'name': 'tom', 'age': 20, 'gender': 'man'}

'''
总结:
    1. 如果两个列表数据个数相同,len统计任何一个列表的长度都可以
    2. 如果两个列表数据个数不同,len统计数据多的列表数据个数会报错,len统计数据少的列表数据个数不会报错
'''

 
再来个栗子:提取字典中的目标数据

counts = {'MBP': 268, 'HP':125,  'DELL':201, 'Lenovo': 199, 'acer': 99}

'''
1. 需求:提取电脑台数大于等于200
获取所有键值对数据,判断v值大于等于200返回
'''

# 返回一个迭代器,内部是元组dict_items([('MBP', 268), ('HP', 'DELL'), ('Lenovo', 199), ('acer', 99)])
print(counts.items())

# 提取字典中目标数据,这个用法非常重要!!!
dict1 = {key:value for key,value in counts.items() if value >= 200}
print(dict1)  # {'MBP': 268, 'DELL': 201}

 
 

8.3 集合推导式

这个用的不多,简单的来个栗子:

# 需求:创建一个集合,数据为下方列表的2次方
list1 = [1,1,2]
set1 = {i ** 2 for i in list1}
print(set1)   # 输出 {1, 4}
# 集合有数据去重功能,所以这个集合数据只有两个数据,分别是1,4

 
 

8.4 推导式总结

三种推导式书写的格式

1. 列表推导式
[xx for xx in range]

2. 字典推导式
{xx1 : xx2  for ... in ...}

3. 集合推导式
{xx for xx in ...}

 
 

9. Python函数

Python函数的使用其实跟C、和Java函数的使用都是大同小异的。

函数的作用: 装代码,高效的代码重用

 

9.1 函数的使用

基本使用

# 1. 定义函数
def sel_func():
    print('I Love Python')

# 2. 函数调用
print('恭喜你登录成功')
sel_func()

'''
注意
	1. 不同的需求,参数可有可无
	2. 在Python中,函数必须先定义后使用
	3. 当调用函数的时候,解释器回到定义函数的地方去执行下方缩进的代码,当这些代码执行完,
	   回到调用函数的地方继续向下执行定义函数的时候,函数体内部缩进的代码并没有执行
'''

 
 
有参数的函数

函数的参数:函数调用的时候可以传入真实数据,增大函数的使用的灵活性
形参:函数定义时书写的参数(非真实数据)
实参:函数调用时书写的参数(真实数据)

# 参数形式传入真实数据,做加法运算
# 这里的a、b是形参
def add_num2(a,b):
    result = a + b
    print(result)

# 10,20是实参
add_num2(10,20)  # 输出30

 
 
函数中return的作用

def buy():
    return '烟'
    # print('ok')   #这一行代码不执行

goods = buy()
print(goods)

'''
return 作用:
			1. 负责函数返回值
			2. 退出当前函数:导致return下方的所有代码(函数体内部)不执行
'''

 
 

9.2 函数的说明文档

就是自己书写函数的时候,可以在函数里写一个说明文档,以后通过这个说明文档可以直接查看这个函数什么作用。

# len是内置函数,早在定义的时候就已经封装好说明文档了
# 自己写的函数没有说明文档,为了方便后期查看这种解释说明的信息更快捷更方便,定义函数的同时,定义一个说明文档就可以了
# 函数内部缩进的第一行书写的多行注释才是说明文档。如果敲了回车,则会更详细的显示(参数和返回值)。

help(len)  # help函数作用:查看函数的说明文档(函数解释说明的信息)
# def sum_num(a,b):
#     ''' 求和函数 '''  # 定义函数的说明文档
#     return a + b
# help(sum_num)

# 函数的说明文档的高级使用。 就是多行注释按回车,会出现参数1、2和renturn,说明他们的作用。
def sum_num1(a,b):
    '''
    求和函数sum_num1
    :param a: 参数1
    :param b: 参数2
    :return: 返回值
    '''
    return a + b
help(sum_num1)

 
 

9.3 函数的嵌套调用

来个栗子感受一下嵌套调用

# 所谓函数嵌套调用指的是一个函数里面有调用了另外一个函数

# 需求:两个函数testA 和 testB  ---- 在A里面嵌套调用B


def testB():
    print('B函数开始-----')
    print('这是B函数')
    print('B函数结束-----')

def testA():
    print('A函数开始')
    # 嵌套调用B
    testB()
    print('A函数结束')

testA()

 
 
打印横线图形


def print_line():
    print('-' * 20)

# 函数嵌套调用,实现多条横线
def print_lines(num):
    i = 0
    while i < num:
        print_line()
        i += 1

print_lines(5)

 
 
任意三个数求平均值

#  任意三个数求平均值
# Python语言当中,做除法运算,不管参与运算的是不是浮点数,只要是除法,结果就是浮点数。

def sum_num(a,b,c):
    return a + b + c
    
def average_num(a, b ,c):
    # 先求和,再除以3
    sumResult = sum_num(a, b, c)
    return sumResult / 3

averageResult = average_num(1, 2, 3)
print(averageResult)   # 输出结果为 2.0

 
 

9.4 变量的作用域

局部访问

# 定义一个函数,声明一个变量:函数体内部访问,函数体外部访问
def testA():
    a = 100
    print(a)  # 函数体内部访问,能访问到a变量

testA()
print(a) # 报错:a变量是函数内部的变量,函数外部无法访问,这里的a是一个局部变量

 
 
访问全局变量

# 声明全局变量:函数体内外都能访问
a = 100 
print(a)

def testA():
    print(a)

def testB():
    print(a)

testA()
testB()

 
 
修改全局变量

# 函数体内修改全局变量

a = 100
print(a)  # 输出100

def testA():
    print(a)

def testB():
    global a
    a = 200
    print(a)

testA()     # 输出100
testB()     # 输出200
print(a)    # 输出200
'''
总结:
    1. 如果在函数里面直接把变量a = 200赋值,此时的a不是全局变量的修改,而是相当于在函数内部声明了一个新的局部变量
    2. 函数体内部修改全局变量:先global声明a为全局变量,然后再变量重新赋值
'''

 
 
多函数执行流程

# 1.声明全局变量 2. 定义两个函数 3.函数1修改全局变量:函数2访问全局变量
glo_num = 0

def test1():
    global glo_num
    glo_num = 100

def test2():
    print(glo_num)


 # 疑问:已经再test1中修改了全局变量,为什么这个地方输出结果不是100?因为进行函数调用,没有执行函数体内的代码。
print(glo_num)  # 输出结果为0
test2()  # 输出的结果为0。还是因为因该全局变量的函数没有执行

test1()  # 执行了函数体内的代码
test2()  # 输出100
print(glo_num)  # 输出100,因为test1函数调用了,修改了全局变量。

 
 

9.5 函数返回值(多返回值)

 
返回值作为参数传递


def test1():
    return 50

def test2(num):
    print(num)

# 先得到函数1的返回值,再把这个返回值传入到函数2
result = test1()
test2(result)

 
 
函数的返回值(多返回值)

# 需求:一个函数有两个返回值1和2
# 一个如果有多个return不能都执行,只执行第一个return:无法做到一个函数多个返回值

# def return_num():
#     return 1
#     return 2
#
# result = return_num()
# print(result)  # 输出结果为1。第二个return不起作用

'''
1. 下面是一个函数多个返回值的正确写法
2. return a,b写法,返回多个数据的时候,默认是元组类型
3. return后面可以连接列表、元组或字典,以返回多个值
'''

def return_num():
    return 1,2   # 返回值是元组
    # return 后面可以直接写元组、列表、字典、返回多个值.
    # return (10,20)  # 返回的是元组
    # return [100,200]  # 返回的是列表
    # return {'name':'Python', 'age': 20} # 返回的是字典
result = return_num()
print(result)  # return 1,2 输出结果是(1, 2)

 
 

9.6 函数的参数的类型

 
位置参数

def user_info(name,age,gender):
    print(f'您的姓名是{name},年龄是{age},性别是{gender}')

user_info('tom',20,'男') # 输出结果为 您的姓名是tom,年龄是20,性别是男

# 注意:传递和定义参数的顺序及个数必须一致
# user_info('tom',20) # 个数定义和传入不一致会报错
# user_info(20,'tom','男')  # 顺序也和定义必须是一致的,否则倒是数据无意义

 
 
关键字参数

# 函数调用,通过"键=值"形式加以指定
def user_info(name,age,gender):
    print(f'您的姓名是{name},年龄是{age},性别是{gender}')

# 1. 调用函数传参
user_info('jack', age=20 , gender='男')   # 您的姓名是jack,年龄是20,性别是男

# 2. 关键字参数之间部分先后循序
user_info('jack', gender='男', age=20)   # 您的姓名是jack,年龄是20,性别是男

# 3. 位置参数必须写在关键字参数的前面
# user_info(age=20 , gender='男', 'jack')  # 报错了。必须关键词放在前面

 
 
缺省参数

'''
1.缺省参数(默认参数):为了节省用户的时间成本,提高用户体验,可以把一些需求上带有默认值的这种参数,设置成一个默认值,这样写法的参数,叫做缺省参数(默认参数)。
2. 所有的位置参数必须出现在默认参数的前面
3. 函数调用时,如果为缺省参数传值则修改默认参数值;否则使用这个默认值
'''

def user_info(name,age,gender='男'):    # gender='男'是缺省参数
    print(f'您的姓名是{name},年龄是{age},性别是{gender}')

# 没有为缺省参数传值,表示使用默认值
user_info('tom', 18)  # 您的姓名是tom,年龄是18,性别是男

# 为缺省参数传值,使用了gender='女 ',即修改了默认值
user_info('tom', 18, gender='女') # 您的姓名是tom,年龄是18,性别是女

 
 
不定长参数之位置参数

'''
1.不定长参数也叫可变参数。用于不确定调用的时候会传递多少个参数(不传也可以)的场景。
  此时可以用包裹位置参数或者包裹关键字参数,来进行参数传递。
2. 传进的所有参数都会被args变量收集,它会根据传进参数的位置合并为一个元组,args是元组类型,这就是包裹位置传递
'''

# 接收所有位置参数,返回一个元组
def user_info(*args):
    print(args)

# 包裹位置传递
# 如果是*args接收不定长的位置参数据,可以传数据,也可以不传数据,无论传与不传,将来接收的都是所有位置参数,返回的是都是一个元组
user_info()              #  ()
user_info('tom')        #  ('tom',)
user_info('tom', 20)     #  ('tom', 20)
user_info('tom', 20,'男')  #  ('tom', 20, '男')

 
 
不定长参数之关键字参数

# 收集所有关键字参数,返回一个字典
# 包裹关键字传递
def user_info(**kwargs):
    print(kwargs)

user_info()
user_info(name='tom')
user_info(name='tom', age=20)

# 无论是包裹位置传递还是包裹关键字传递,都是一个组包的过程

 
 
扩展1:拆包

上面说了不定长参数是组包的过程,那就来说一下拆包的过程


# 1. 拆包元组数据
# def return_num():
#     return 100, 200

# result = return_num()
# print(result)    # 输出 (100, 200)

# num1, num2 = return_num()
# print(num1)   # 输出 100
# print(num2)   # 输出 200

# 2. 字典数据拆包:变量存储的数据是key值
# 先准备字典,然后拆包
dict1 = {'name': 'tom', 'age': 20}
# dict1中有两个键值对,拆包的时候用两个变量接收数据
a , b = dict1
print(a)     # 输出name
print(b)     # 输出age

# 提取value的值
print(dict1[a])     # 输出tom
print(dict1[b])     # 输出20
print(dict1['name'])  # 输出tom

 
 
扩展2:交换变量的值

# 方法1:
a= 10
b = 20

c = 0
c = a
a = b
b = c

print(a)   # 20
print(b)   # 10

# 方法2:
a, b = 1, 2
print(a)  # 输出1
print(b)  # 输出2

a, b = 1, 2
a, b = b, a
print(a)  # 输出2
print(b)  # 输出1

 
 

9.7 引用作实参

 
体验引用

# 变量就是存储数据的名字而已,这个名字就可以理解为引用,再python语言中数据其实传递来传递去都是通过变量的形式来传递的
# 简单粗暴的理解,引用就是变量名。引用可以当作实参传入到函数里面

# 1. 不可变类型:int
# 1.1 声明变量保存整型数据,把这个数据赋值到另一个变量:id()检测两个变量的id值(内存的十进制值)
a = 1
b = a
print(b)     # 输出1
# 发现a和b的id值相同的
print(id(a))   # 输出 140708418216784
print(id(b))    # 输出 140708418216784

# 修改a的数据测试id值
a = 2

print(b)   # 输出1

# 因为修改了a的数据,内存要开辟另外一份内存存储2,id()检测a和b的地址不同
print(id(a))  # 输出 140708418216816
print(id(b))  # 输出 140708418216784


============================================================================

# 2. 可变类型:列表

aa = [10, 20] 
bb = aa
print(bb)       # [10, 20]

print(id(aa))    # 2266328490632
print(id(bb))	# 2266328490632

# 增加数据
# 列表是可变类型
aa.append(30)
print(aa)   # [10, 20, 30]
print(bb)   # [10, 20, 30]

print(id(aa))  # 2266328490632  地址值
print(id(bb))  # 2266328490632

 
引用当作实参

def test(a):
    print(a)
    print(id(a))

    a += a
    print(a)
    print(id(a))

b = 100
test(b)    # 这是不可变类型数据

c = [11, 22]
test(c)    # 这是可变类型数据

 
 

9.8 可变和不可变类型汇总

 
小总结:

'''
数据的可变类型:如果对数据进行修改,修改的是原数据,这样的数据是可变类型
数据的不可变类型:如果数据修改的时候改的不是原数据,这样的数据是不可变类型。

可变类型:
    列表
    字典
    集合
不可变类型:
    整型
    浮点型
    字符串
    元组
    
重点: 作用域、函数多返回值、函数的参数

'''

 
 

9.9 递归函数和匿名函数(lambda)

 
递归函数的应用


# 递归函数:1.内部自己调用自己  2.必须有出口
# 递归是一种编程思想,函数是编程的一种体现
# return有两个作用: 1. 返回值 2. 退出当前函数

'''
需求:3以内数字累加和3 + 2 + 1 = 6
6 = 3 + 2以内数字累加和
2以内的累加和 = 2 + 1以内的累加和
1以内的累加和 = 1   # 出口
'''

def sum_numbers(num):
    # 2.出口
    if num == 1:
        return 1
    # 1. 当前数字 + 当前数字减一的累加和
    return num + sum_numbers(num - 1)

result = sum_numbers(3)
print(result)

# 如果没有出口,报错:超出最大递归深度

 
 
匿名函数lambda,来个栗子感受一下

'''
应用场景:
    1.lambda的作用就是简化代码
    2.如果一个函数有一个返回值,并且只有一句代码,可以使用lambda简化
语法:lambda 参数列表 :表达式
注意:
    lambda表达式的参数可有可无,函数的参数在lambda表达式中完全适用
    lambda表达式能接收多个参数但只能返回一个表达式的值
'''

# 需求:函数 返回值100
# 1. 函数
# def fn1():
#     return 100
#
# result = fn1()
# print(result)


# 2. lambda 匿名函数,就是不在用def语句定义的函数。如果要声明匿名函数,则要使用lambda关键字
# lambda参数列表:表达式
fn2 = lambda : 100
print(fn2)   # lambda内存地址
# 100返回值 调用函数
print(fn2())   # 100

 
 
lambda的参数形式

# 1.无参数
# fn1 = lambda: 100
# print(fn1())

# 2. 一个参数
# fn2 = lambda a: a
# print(fn2('hello world'))

# 3. 默认参数/缺省参数
# fn3 = lambda a, b, c = 200 : a + b + c
# print(fn3(10, 20))
# print(fn3(10, 20, 300))

# 4. 可变参数:*args
# fn4 = lambda *args: args
# print(fn4(10))
# print(fn4(10, 20))
# print(fn4(10,20,30,40))    # (10, 20, 30, 40)

# 5. 可变参数: **kwargs
fn5 = lambda **kwargs : kwargs
print(fn5(name = 'Python'))
print(fn5(name = 'Python', age = 30))   # {'name': 'Python', 'age': 30}

 
 
带判断的lambda

# lambda应用
# 1. lambda 两个数字比大小,谁大返回值

fn1 = lambda a, b : a if a > b else b
print(fn1(1000, 500))   # 1000

 
 
列表数据排序

'''
students是一个序列名,指代的就是列表序列,key等于一个 lambda的表达式,
这里面就用到了lambda,sort里面有个参数key,如果列表里面有字典,按照字典某个key进行排序用的。
将来要进行升或降序排序的数据,这里指得是字典,返回值,排序的依据是name key还是age key
里面形参x指代的是所有的字典,
'''
students = [
    {'name':'tom','age':20},
    {'name':'jock','age':21},
    {'name':'rose','age':22}
]

# 1. name key对应的值进行降序排序
students.sort(key=lambda x: x['name'])
print(students)
# 2. age key对应的值进行升序排序
students.sort(key=lambda x: x['age'])
print(students)
# 3. age key对应的值进行降序排序
students.sort(key=lambda x: x['age'],reverse=True)
print(students)

 

lambda小总结

'''
一、 lambda 
   (1)语法
        lambda 参数列表: 表达式
        
    (2)lambda的参数形式
    
        无参数:
            lambda: 表达式
            
        一个参数(多个参数用逗号隔开):
            lambda 参数:表达式
            
        默认参数:
            lambda key=value:表达式
            
        不定长位置参数:
            lambda *args:表达式
            
        不定长关键字参数:
            lambda **kwargs:表达式
'''

 
 

10. 学生管理系统

根据前面所学的知识,把知识综合起来,来做一个简单的学生管理系统。

# 定义功能界面
def info_print():
    print('请选择功能------------------')
    print('1. 添加学生')
    print('2. 删除学生')
    print('3. 修改学生')
    print('4. 查询学生')
    print('5. 显示所有学生')
    print('6. 退出系统')
    print('-' * 20)

info = []
# 所有的功能函数都是操作学生信息,所有存储所有学生信息应该是一个全局变量,数据类型为列表。


#  添加学生信息的函数
def add_info():
    """添加学生函数"""     # 添加函数的说明文档
    pass                 # 当我们还不知道函数体内部要写什么代码的时候,加一个pass作占位,,避免语法出现错误。
    # 1.用户输入:学号、姓名、手机号
    new_id = input('请输入学号:')
    new_name = input('请输入姓名:')
    new_tel = input('请输入手机号:')

    # 2. 判断是否添加这个学生,如果学生姓名已经存在报错提示;如果姓名不存在则添加数据
    global info

    # 2.1 不允许姓名重复:判断用户输入的姓名 和 列表里面字典的name对应的值相等,提示
    for i in info:
        if new_name == i['name']:
            print('此用户已经存在')
            # return作用:退出当前函数:准备空字典,字典新增数据,列表追加字典
            return

    # 2.2 如果输入的姓名不存在,添加数据:准备空字典,字典新增数据,列表追加数据
    info_dict = {}

    # 字典新增数据
    info_dict['id'] = new_id
    info_dict['name'] = new_name
    info_dict['tel'] = new_tel
    # print(info_dict)

    # 列表追加字典
    info.append(info_dict)
    print(info)


# 删除学生
def del_info():
    """删除学生"""
    del_name = input('请输入要删除学生的姓名:')
    global info   # 声明全局变量
    for i in info:      # 遍历列表
        if del_name == i['name'] :
            # 如果姓名存在,则在列表删除数据
            info.remove(i)
            break
    else:        # else的作用:当循环正常结束要执行的代码。就是遍历完列表中的数据,还没有break。
        print('该学员不存在!!!')
    print(info)



# 修改函数
def modify_info():
    """修改学生信息"""
    modify_name = input('请输入要修改的学生的姓名:')
    global info
    for i in info:
        if modify_name == i['name']:
            i['tel'] = input('请输入新的手机号:')
            break
    else:
        print('该学生不存在!!!')
    # 打印info
    print(info)


# 查询学员信息
def search_info():
    """查询学生信息"""
    search_name = input('请输入要查询的学生的姓名:')
    global info  # 声明全局变量
    for i in info:
        if search_name == i['name'] :
            print('查询到的学生信息如下--------------------------')
            print(f"学生的学号:{i['id']} , 姓名:{i['name']},   手机号:{i['tel']}")
            break
    else:
        print('查无此人.....')


# 显示所有学生信息
def print_all():
    '''显示所有学生信息'''
    print('学号\t姓名\t手机号')
    # 打印所有学生的数据
    for i in info:
        print(f"{i['id']}\t{i['name']}\t{i['tel']}")




while True:
# 1. 显示功能界面
    info_print()

# 2. 用户输入功能序号
    user_num = int(input('请输入功能序号:'))

# 3. 按照用户输入的功能序号,执行不同的功能(函数)

    if user_num == 1:
        # print('添加')
        add_info()
    elif user_num == 2:
        # print('删除')
        del_info()
    elif user_num == 3:
        # print('修改')
        modify_info()
    elif user_num == 4:
        # print('查询')
        search_info()
    elif user_num == 5:
        # print('显示所有')
        print_all()
    elif user_num == 6:
        # 退出系统
        exit_flag = input('确定要退出吗?yes or no:')
        if exit_flag == 'yes':
            break   # break是最主要的
    else:
        print('输入的功能序号有误')

# 这个退出系统功能,不用函数去做,1.代码比较简单 2.有一个必要的功能,封装到函数里面可能会出问题
# 退出系统依赖于break,break是当一定条件成立,终止循环用的。终止的是就近的这一层循环,如果把这些代码封装
# 一个函数里面去,这个时候跟while True循环不在一起了,就有可能发生问题的。

 
 

11. 高级函数

 
高阶函数作用: 为了化简代码,增加函数的灵活性
 

11.1 abs()和round()函数

这两个函数的用法比较简单,来个栗子就会了。but这两个函数不是高阶函数


# abs() 求绝对值用的
print(abs(-10))  # 10


# round()  四舍五入的计算
print(round(1.2))  # 1
print(round(1.6))  # 2

# abs()和round()不是高阶函数

 
 

11.2 内置高阶函数(map、reduce、filter)

 
先来体验一下高阶函数

# 需求: 任意两个数字,先进行数字处理(绝对值或四舍五入)在求和运算

# 1. 写法一
def add_num(a,b):
    # 绝对值
    return abs(a) + abs(b)

result = add_num(-1.1, 1.0)
print(result)    # 2.1

# 2. 写法二
def sum_num(a, b, f):
    return f(a) + f(b)

result1 = sum_num(-1,-2,abs)
print(result1)  # 3

result2 = sum_num(1.2, 1.4, round)
print(result2)  # 2

# 方法二的代码更加简洁,函数灵活性较快
# 函数式编程大量使用函数,减少了代码的重复,因此程序比较短,开发速度较快
'''
高阶函数:把函数作为参数传入,这样的函数称为高阶函数,高阶函数是函数式编程的体现。函数式编程就是指这种高度抽象的编程范式。
高阶函数其实作用就是为了化简代码,增加函数的灵活性
'''

 
 
map()函数

'''
map(func, lst),将传入的函数变量func作用到lst变量的每个元素中,并将结果组成新的列表(Python2)/
迭代器(Python3)返回
'''

# 1. 准备列表数据
list1 = [1, 2, 3, 4, 5]

# 2. 准备2次方计算的函数
def func(x):
    return x ** 2

# 3. 调用map
result = map(func, list1)

# 4. 验收成果
# 在打印迭代器的时候,只能返回内存地址,这时要用list()转换数据类型
print(result)     # 输出 <map object at 0x00000208211131D0>
print(list(result))  # [1, 4, 9, 16, 25]


 
 
reduce函数

'''
reduce(func, lst),其中func必须有两个参数. 每次func计算的结果继续和序列的下一个元素作累计计算.
注意: reduce()传入的参数func必须接收2个参数
'''

list1 = [1, 2, 3, 4, 5]
# 1. 导入模块
import functools

# 2.定义功能模块
def func(a, b):
    return a + b

# 3. 调用reduce. 作用:功能函数计算的结果和序列的下一个数据作累计计算
result = functools.reduce(func, list1)
print(result)    # 输出结果为 15    


 
 
filter()函数

'''
filter(func, lst)函数用于过滤序列,过滤掉不符合条件的元素,返回一个filter对象. 如果要转换为列表,可以使用list()来转换
'''
list1 = [1,2,3,4,5,6,7,8,9,10]

# 1. 定义功能函数:过滤序列中的偶数
def func(x):
    return x % 2 == 0

# 2. 调用filter
result = filter(func,list1)
print(result)       # <filter object at 0x000002AEA49031D0>
print(list(result))      # [2, 4, 6, 8, 10]

Logo

权威|前沿|技术|干货|国内首个API全生命周期开发者社区

更多推荐