Python学习_2(函数篇)

一、函数

  • 模块化编程
    模块化编程指把程序进行封装(函数封装、面向对象、文件…)
  • 函数
    函数是一个具有特定功能的代码块,就是将代码进行封装,提高代码的重用性,提高开发效率
  • 函数的定义
# 定义函数 [基本结构]
def 函数名([参数列表]):
    功能代码
    ...
    
# 函数定义后并不会执行,需要进行调用
函数名()  
  • 函数的特征和注意
1. 函数定义后,不调用不执行
2. 不能在函数定义前调用函数
3. 函数的调用不受次数影响
4. 函数的命名要遵守命名规范
    字母数字下划线,不用数字开头
    严格区分大小写,不能使用关键字
    命名最好有意义,且不要使用中文
    函数名不能有冲突,冲突后会被覆盖
1. 函数的参数
'''
命名关键字参数:
    1. 关键字参数定义在 收集参数 后面
    2. 关键字参数必须通过形参的名字来进行传递
'''
def func(a,b,c=3,*args,name):
    print(a,b,c)
    print(args)
    print(name)

func(1,2,7,4,5,6,7,8,9,name="me")
'''
1 2 7
(4, 5, 6, 7, 8, 9)
me
'''
# 在调用函数时,需要按照顺序进行参数的传递
# 也可以把普通函数的普通参数按照关键字参数进行传递
def func1(age,height): 
    print(age)   
    print(height)

func1(height=180,age=19)  # 19 180
'''
关键字收集参数
'''
def func2(a,b,c=3,*args,name,**kwargs):
    print(a,b,c)
    print(args)   # 普通收集参数,会把多余的参数收集成 元组
    print(name)
    print(kwargs)  # 关键字参数收集,会把多余的关键字参数收集为字典

# 注意形参声明的位置: 普通参数 --> 默认参数 --> 收集参数 --> 关键字参数 --> 关键字收集参数
func2(1,2,4,112,113,name="aaa",age=222,sex="男")
'''
1 2 4
(112, 113)
aaa
{'age': 222, 'sex': '男'}
'''
2. 函数的返回值

– 函数除了可以完成一定的功能外,还可以按需要返回一些内容,使用return关键字来指定返回的参数,可以返回任意类型的参数
– 函数的返回值会把数据返回调用处,可以使用变量接收

'''
函数的返回值
    return 意味着函数的结束,之后的代码不执行
    1. 执行过程函数:函数内完成一定功能,没有返回值
    2. 有返回值的函数,函数内完成一定功能,并返回一个结果到函数调用处
'''
def hi(a,b):
    res = (f"{a} love {b}")
    return res

def hi1(a,b):
    res = (f"{a} love {b}")

say=hi("fa","mo")
print(say)  # fa love mo

say=hi1("羊","狼")
# 函数中没有使用return或者return后没有任何内容,那么默认返回none
print(say,type(say))  # None <class 'NoneType'>
3. 变量的作用域
'''
变量作用域:变量的有效范围
全局变量:在函数内外都可以使用的变量
    1. 在函数内部使用global关键字定义的变量就是全局变量
    2. 在函数外定义的变量,在函数内使用global关键字进行声明,那么也是全局变量
局部变量:函数内部可以使用的变量

globals(): 获取全局数据,在任何位置都可获取
locals(): 获取当前作用域的数据

注意:
1. 函数内可以直接获得函数外部的变量
2. 函数内不可直接更改函数外的变量
3. 函数内定义的变量(局部变量),函数外不能使用

变量分两种:
    1.可变数据类型:在函数外定义的变量,在函数内可以使用和更新
        列表和字典
    2.不可变数据类型:在函数外定义的变量,在函数内只能访问,不能使用其他操作
'''
num=10
varlist=[1,2,3]
vardict={'a':'a','b':'b'}
def func3():
    print(num)  # 10 函数内可以直接获得函数外部的变量
    # num+=20   在函数内不可直接更改函数外的变量
    nei="pao"
    print(nei)
    # 可变数据类型
    varlist[2] = "狗"
    print(varlist)  # [1, 2, '狗']
    vardict['a'] = 'aa'  # {'a': 'aa', 'b': 'b'}
    print(vardict)

    # 在函数内部使用global关键字定义的变量就是全局变量
    global live
    live = 'keep going'


func3()
# print(nei)  not defined 函数内定义的变量(局部变量),函数外不能使用
print(varlist)  # [1, 2, '狗']
print(live)  # keep going
4. nonlocal 关键字
'''
nonlocal 关键字
# 变量和函数都有作用域
# 在内函数中如何使用上一层函数中的局部变量?
    使用 nonlocal 关键字引用
'''

# 定义一个外函数
def outer():
    '''
    这里是用来写当前函数的文档说明的
    需要说明当前函数的作用
    如果当前函数还有形参,那么还需要对形参进行一一说明
    :return: 此处说明当前函数的返回值
    '''
    # 外函数的局部变量
    num = 10
    def inner():
        # nonlocal 关键字在局部函数中使用
        nonlocal num  # 引用上一层函数中定义的局部变量,但依然不能提升为全局变量
        num += 1
        print(num)
    inner()

outer()

print(__name__)  # 获取当前脚本的文件名
print(__doc__)   # 获取当前脚本的说明文档 (第一个''''''引用的内容)
print(outer.__doc__)   # 获得当前函数的说明文档
5. 高阶函数
5.1 递归函数
'''
递归函数:
    递归函数就是定义了一个函数,然后在函数内,自己调用自己的这个函数
    递归函数内必须要有结束,不然会导致栈溢出
    递归函数是一层一层地进入,再一层一层地返回
'''

def func1(num):
    print(num)
    if num >0:  # 判断递归调用的条件
        func1(num-1)
    print(num) # 一层一层返回 0 1 2 3

func1(3)  # 3 2 1 0 1 2 3

print("======================")
# 递归实现一个数的阶乘 1*2*3*4*5
res=1
def func2(num):
    if num == 1:
        return 1
    else:
        return num*func2(num-1)

res = func2(4)
print(res)  # 24

# 递归实现斐波那契数列,求第n位上的数是多少? 1,1,2,3,5,8,13...
def fei(n):
    if n==1 or n==2:
        return 1
    else:
        return fei(n-1)+fei(n-2)

res3 = fei(6)
print(res3) # 8
5.2 回调函数
'''
回调函数
    函数中的参数可以是任意类型的,如果在一个函数中要求传递的参数是一个函数作为参数,
    并且在函数中使用了传递进来的函数,那额这个函数就是回调函数
'''
# 定义一个函数,函数中的一个参数要求是另一个函数
def hd(f):
    print(f, type(f))


def love():
    print("123")

hd(love)  # <function love at 0x00C8C0B8> <class 'function'>
5.3 闭包函数
'''
闭包函数
    既然可以把函数作为一个形参进行传递,作为回调函数,那么如果在一个函数中,返回一个函数呢?
    在一个函数内返回了一个内函数,并且这个返回的内函数还使用了外函数中的局部变量,这就是闭包函数

闭包的特点:
    1. 在外函数中定义了局部变量,并且在内部函数中使用了这个局部变量
    2. 在外函数中返回内函数,返回的内函数就是闭包函数
    3. 闭包的作用: 保护了函数中的变量不受外部的影响,但是又能够不影响使用
'''
# 外函数
def person():
    money = 0  # 局部变量
    # 内函数
    def work():
        nonlocal money  # 在内函数中使用了外函数的临时变量
        money+=100
        print(money)
    # 在外函数中返回了内函数,这个内函数就是闭包函数
    return work

res = person()  # retuen work
res()  # res() == work()
res()  # 200

# 检测一个函数是否为闭包函数,函数名.__closure__如果是闭包函数返回cell
print(res.__closure__) # (<cell at 0x019CD910: int object at 0x014E7CF0>,)
5.4 匿名函数
'''
匿名函数 lambda表达式
    匿名函数的意思即可以不使用def定义,并且这个函数也没有名字
    在python中可以使用lambda表达式来定义匿名函数
    注意: lambda表达式仅仅是一个表达式,不是一个代码块,所有lambda又称为一行代码的函数
    lambda表达式也有形参,并且不能访问除了自己形参之外的任何数据包括全局变量
    lambda不能写太复杂的逻辑,功能相对单一

语法:
    lambda [参数列表]:返回值
'''

res = lambda x,y:x+y
print(res(4,2))
# 带有分支结构的lambda表达式
# lambda 参数列表: 真区间 if 表达式判断 else 假区间
res = lambda sex:"henman" if sex=="男" else "nice"
print(res("nv"))
5.5 迭代器
'''
迭代器
    迭代器是python中最具特色的功能之一,是访问集合元素的一种方式
    迭代器是一个可以记住遍历访问的位置的对象
    从集合的第一个元素访问,直到集合中的所有元素被访问完毕
    迭代器只能从前往后一个一个遍历,不能后退
    能被next()函数调用,并不断返回下一个值的对象称为迭代器(iterator 迭代器对象)
'''
# range(10) 0--9 返回一个可迭代的对象
  • iter()
'''
iter() 
    功能:把可迭代的对象,转换为一个迭代器对象
    参数:可迭代的对象 (str,list,tuple,dict,set,range...)
    返回值:迭代器对象
    注意:迭代器一定是可以迭代的对象,但是可迭代对象不一定是迭代器
'''
# 定义一个列表,是一个可迭代的对象
arr = ["赵四", "刘能", "沈阳", "拉面"]
# for i in arr:
#     print(i)

# 把可迭代对象转换为迭代器使用
res = iter(arr)
print(res, type(res))  # <list_iterator object at 0x0141DBC8> <class 'list_iterator'>
r = next(res)
print(r)  # 赵四
print(next(res))
print(next(res))
print(next(res)) # 拉面
# print(next(res)) 超出可迭代的范围 StopIteration
r = list(res)
print(r)  # []
  • 迭代器取值
'''
迭代器取值的方案
    1. next() 调用一次获取一次,直到数据被取完
    2. list() 使用list函数直接取出迭代器中的所有数据
    3. for    使用for循环遍历迭代器的数据

迭代器取值的特点: 取出一个少一个,直到都取完,最后再获取就会报错
'''
# 使用list取值
r = list(res)
print(r)  # []

# 使用for
for i in res:
    print(i)
  • 检测迭代器和可迭代对象
'''检测迭代器和可迭代对象的方法'''
# 迭代器一定是一个可迭代的对象,可迭代对象不一定是迭代器
from collections.abc import Iterator, Iterable
varstr = '123456'
res = iter(varstr)

# type()  函数返回当前数据的类型
# isinstance()  检测一个数据是不是一个指定的类型
r1 = isinstance(varstr,Iterable)  # True 是一个可迭代对象
r2 = isinstance(varstr,Iterator)  # False 不是一个迭代器

# next()
next(varstr)  # 'str' object is not an iterator
print(r1)
print(r2)
6. 内置函数
  • 内置函数是系统安装完python解释器时,由python解释器给提供好的函数
6.1 range()
'''
range() 函数
功能:能够生成一个指定的数字序列
参数:start, stop[, step]
返回值:可迭代的对象,数字序列
'''
res = range(10)
print(list(res))  # [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
for i in res:
    print(i)

res = range(1,10,2)
print(list(res))  # [1, 3, 5, 7, 9]

# 获取一个倒序的数字序列
res = range(10,1,-2)
print(list(res))  # [10, 8, 6, 4, 2]

res = range(-10,-20,-1)
print(list(res))  # [-10, -11, -12, -13, -14, -15, -16, -17, -18, -19]
6.2 zip()
'''
zip()
    功能:zip函数是可以接收多个可迭代的对象,然后把每个可迭代对象中的第i个元素组合在一起,形成一个新的迭代器
    参数:*iterables,任意个数的可迭代对象
    返回值:返回一个元组的迭代器
    
zip() 与 * 运算符相结合可以用来拆解一个列表
'''
var1 = [1, 2, 3, 4]
var2 = ['a', 'b', 'c', 'd']
var3 = ('A', 'B', 'C', 'D')
# 调用zip函数,组成新的元组迭代器
res = zip(var1, var2, var3)
print(res, type(zip()))  # <zip object at 0x01D30E88> <class 'zip'>
# print(list(res))  # [(1, 'a', 'A'), (2, 'b', 'B'), (3, 'c', 'C'), (4, 'd', 'D')]
for i in res:
    print(i)

x = [1, 2, 3]
y = [4, 5, 6]
zipped = zip(x, y)
print(list(zipped))  # [(1, 4), (2, 5), (3, 6)

print(zip(x,y))  #  迭代器对象:<zip object at 0x00E60D28>
print(*zip(x, y))  #  组合好的多个元组数据 (1, 4) (2, 5) (3, 6)

x2, y2 = zip(*zip(x, y))  # (1, 2, 3) (4, 5, 6)
print(x2,y2)
# x == list(x2) and y == list(y2)
# True
6.3 数学相关函数
  • 数学计算函数
'''数学相关函数'''
# 返回一个数的绝对值
print(abs(-10))  # 10

# 求和 sum(iterable[, start]) 参数是一个可迭代对象
print(sum([1,2,3]))

# 返回最大值
print(max([1,2,3]))  # 3
print(max(99,12,45))  # 99

# 幂运算 pow(x,y) 返回x的y次方
print(pow(2,3))  # 8

# 四舍五入 round(number[, ndigits]) 返回number舍入到小数点后ndigits位精度的值。如果ndigits被省略或为None
# 四舍六入 五留双 (如果与两个倍数的距离相等,则选择偶数 奇进偶退)
r = round(3.1415926,3)
print(r)  # 3.142
print(round(4.5))  # 4
print(round(5.5))  # 6
  • 进制相关函数
'''进制相关函数'''
# bin() 将数值类型转为二进制
print(bin(123))  # 0b1111011
# int() 将二进制转为十进制
print(int(0b1111011))  # 10
# oct() 转为八进制
print(oct(123))  # 0o173
# hex() 转为十六进制
print(hex(123))  # 0x7b
  • ascii 字符转换
'''ASCII 字符转换
A - Z 65-90
a - z 97-122
0 - 9 48-57
'''
# 将字符转为ascii ord()
print(ord('a'))  # 97
# 将ascii转为字符  chr()
print(chr(97))  # a
6.4 高阶函数
  • sorted()
'''
sorted()
    运行原理:把可迭代数据里面的元素,一个一个取出来,放到key这个函数中进行处理,并按照函数中return的结果进行排序,返回一个新的列表
    功能:排序
    参数:
        iterable    可迭代的数据(容器类型数据,range数据序列,迭代器)
        reverse     可选,是否反转,默认为false(不反转)
        key         可选,可以是自定义函数,也可以是内置函数
    返回值:排序后的结果
'''
arr = [3,7,1,-9,20,10]
res = sorted(arr)
print(res)  # [-9, 1, 3, 7, 10, 20]  默认
res1 = sorted(arr,reverse=True)
print(res1)  # [20, 10, 7, 3, 1, -9]  反转
# 使用abs() 这个函数作为sorted的key关键字参数使用
res3 = sorted(arr,key=abs)  # 3 7 1 9 20 10
print(res3)  # [1, 3, 7, -9, 10, 20]
# 使用自定义函数 作为sorted的key关键字参数使用
def func(num):
    return num % 2
arr = [3,2,4,6,5,7,9]
res4 = sorted(arr,key=func)  # 1 0 0 0 1 1 1
res5 = sorted(arr,key=lambda x:x%2)  # 这里自定义函数可以简化为lambda函数
print(res4)   # [2, 4, 6, 3, 5, 7, 9]
print(res5)   # [2, 4, 6, 3, 5, 7, 9]
  • map()
'''
map(function, *iterables)
    功能:对传入的可迭代数据中每个元素进行处理,返回一个新的迭代器
    参数:
        func 函数  自定义函数|内置函数
        iterables: 可迭代的数据
    返回值:迭代器
'''
varlist = ['1','2','3','4']
# newlist = []
# for i in varlist:
#     newlist.append(int(i))
# print(newlist)
res = map(int,varlist)  # varlist中的每个元素都用int函数进行处理,返回新的迭代器
# print(list(res))  # <map object at 0x01A5D5C8> [1, 2, 3, 4]

res1 = map(lambda x:x**2,list(res))
print(list(res1))  # [1, 4, 9, 16]
  • reduce()
'''
reduce(func, *iterables)
    功能:每一次从iterable中拿出 两个 元素,放入到func函数中进行处理,得出一个计算结果,然后将计算结果和iterable中的第三个元素,
        放入到func函数中继续运算,得出的结果和之后的第四个元素运算,以此类推...
    参数:
        func 函数  自定义函数|内置函数
        iterables: 可迭代的数据
    返回值: 最终的运算处理结果
    注意: 使用reduce函数时,需要导入 from functools import reduce
'''
varlist1 = [5,2,1,1]
def func(x,y):
    return x*10+y
'''
5211
5 * 10 + 2 == 52
52 * 10 + 1 == 521
521 * 10 + 1 == 5211
'''
res = reduce(func,varlist1)
print(res)  # 5211

# 不使用int函数,将'456' ==> 456
def myfunc(s):
    vardict = {'1': 1, '2': 2, '3': 3, '4': 4, '5': 5, '6': 6, '7': 7, '8': 8, '9': 9}
    return vardict[s]
# 1.先用map函数把字符转换为数字
iter1 = map(myfunc,'456')
# print(iter1) # <map object at 0x01C5DCE8>
# print(list(iter1))  # [4, 5, 6]
# 2.把数字列表中的值,使用lambda进行二次处理
res = reduce(lambda x,y:x*10+y,iter1)
print(res)  # 456
  • filter()
'''
filter(func, iterable)
    功能:过滤数据,把iterable中的每个元素拿到func函数中进行处理,如果函数返回true则保留这个数据,返回false则丢弃这个数据
    参数:
        func 函数  自定义函数|内置函数
        iterables: 可迭代的数据
    返回值:保留下来的数据组成的迭代器
'''
# 保留所有的偶数,丢弃所有奇数
var3 = [1,2,3,4,5,6,7,8,9]
# def ou(x):
#     if x%2==0:
#         return True
#     else:
#         return False
res = filter(lambda x:True if x%2==0 else False,var3)
print(list(res))  # [2, 4, 6, 8]
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值