python函数-18

1、函数

开发程序的时候,若多个地方需要用到同一块代码块,为了提高编写的效率,把这些代码块进行封装集成到某个地方,便于多次的调用,这就是函数。

1.1、函数定义

语法:

def 函数名():
    封装的逻辑

函数需要用def作为开头,算作标识。函数名的定义规则跟变量命名一样,需要见名知意,之后再按照命名规范来。函数名后一定要加小括号(),小括号后跟冒号:。之后,新开一行进行缩进,缩进后写封装的逻辑。

1.2、函数调用

函数定义好后,如何使用呢?

函数名() 的方式即可调用写好的函数。

示例:

def print_info():
    print("*" * 20)
    print("*")
    print("*")
    print("*")
    print("*" * 20)

print_info()
print("调用函数成功")

1.3、函数注释

这里有两种注释方法。

第一种:

将函数注释写在定义的函数上方。

示例:

写完注释后,将鼠标左键放在上面,会出现这种提示框。

第二种:

将注释写到函数内部,注意注释需要放在前面。

第二种方法最常用。

示例:

def print_info():
    '''
    函数注释:
    函数名:print_info
    功能:打印信息
    '''
    print("*" * 20)
    print("*")
    print("*")
    print("*")
    print("*" * 20)
help(print_info)

通过help方法可以打印注释。

1.4、函数参数

若函数需要对数据进行处理,那么数据从哪里来呢?

答案就是:参数。

参数分为两种,一种为:形参。另一种为实参。

示例:

def use_methods(parm1,parm2):
    assert isinstance(parm1,int)
    assert isinstance(parm2,int)
    if parm1 > parm2:
        print(f"Max is {parm1}")
    else:
        print(f"Max is {parm2}")
int_value1 = 10
int_value2 = 20

use_methods(int_value1,int_value2)

示例中的parm1和parm2就是形参,它没有实际的意义,只有形式意义。它的存在可以理解为占位,等待实际参数的传递。int_value1和int_value2就是实参,它们是这个函数实际处理的数据。这个函数的功能就是比较大小,但如果像示例一样没加注释,初学者可能看不懂,传的值也未必是数字,因此需要加上断言防止用户传错值。

1.5、传递参数的类型:

可变类型和不变可类型。

不可变类型:传递不可变类型的参数,即使对形参的值进行更改,也不会改变原来的值。

示例:

def func_type(int_value):
    if int_value > 10:
        int_value = 999
    else:
        int_value = -999
    print(int_value)

int_value = 8
func_type(int_value)
print(int_value)

对于不可变类型的参数,你可以理解为传递了一个复制体,其本身是不会被修改的,因为内存地址的值不允许改变,改变了就新开辟一个内存地址。

可变类型:传递可变类型的参数,一旦形参的值变了,原来的值也会变。

示例:

def func_type(list_value):
    list_value[0] = 999
    print(list_value)

list_value = [1,2,3]
func_type(list_value)
print(list_value)

可变数据类型可以理解为将自己传递到形参中,因为可变数据类型可以更改内存的值。学过指针概念的,其相当于传一个指针到函数中。

1.6、函数返回值

函数完成功能后,需要给调用者返回一些结果,称返回值。

语法:

def 函数名():
    封装的逻辑
    
    return 某个值

示例:

def return_value(parm1,parm2):
    max_one = 0
    if parm1 > parm2:
        max_one = parm1
    else:
        max_one = parm2
    return max_one
int_value1 = 10
int_value2 = 20
max = return_value(int_value1,int_value2)
print(max)

return的作用不仅仅只是返回一个值,也代表着函数的结束

当函数中执行到return这里,不管后面还有啥逻辑代码,都会跳过,直接跳出整个函数。

示例:

def return_value(parm1,parm2):
    if parm1 > parm2:
        return parm1
    else:
        return parm2

int_value1 = 10
int_value2 = 20
max = return

每次执行到return的时候,后面的直接跳过了。

当然,return不仅仅可以返回一个值,也可以返回多个值。

示例:

def return_value(parm1,parm2):
    if parm1 > parm2:
        return parm1,parm2
    else:
        return parm2,parm1

int_value1 = 10
int_value2 = 20
max1,max2 = return_value(int_value1,int_value2)
print(max1,max2)

根据不同的返回值,接收数据的形式也不一样。

示例:

def return_value(parm1,parm2):
    if parm1 > parm2:
        return [parm1,parm2]
    else:
        return [parm2,parm1]

int_value1 = 10
int_value2 = 20
[max1,max2] = return_value(int_value1,int_value2)
max = return_value(int_value1,int_value2)
print(max1,max2)
print(max)

可以解构形式的接收,也可以整体接收。

1.7、参数类别

Python中函数参数分为:位置参数、默认参数、可变参数、关键字参数和命名关键字参数

位置参数:就是按照形参的顺序,依次传值,不能多也不能少。

示例:

#位置参数
def pos(parm1,parm2):
    return parm1,parm2

int_value1 = 10
int_value2 = 20
max1,max2 = pos(int_value1,int_value2)
print(max1,max2)
max1,max2 = pos(int_value1)
max1,max2 = pos(int_value1,int_value2,int_value1)

默认参数:形参可以设定一个默认值,传值时如果不传,默认参数会使用默认值。

示例:

def default_value(parm1,parm2 = 20):
    return parm1,parm2

parm1,parm2 = default_value(10)
print(parm1,parm2)
parm1,parm2 = default_value(10,30)
print(parm1,parm2)

注意:默认参数必须放置于位置参数后面,放前面会报错。且,默认参数最好用不可变类型的数据,避免逻辑出错。


可变参数:传入的参数数量是可变的。通过*args的方式,会将传入的值放入元组中。(元组不能修改)

示例:

def change_value(*args):
    print(type(args))
    for value in args:
        print(value)

change_value(1,2,3,4,5)
change_value(*[1,2,3,4])

传值的时候可以一个个传,也可将列表、元组这种可迭代对象传入,注意前面加个*,标识。


关键字参数:允许传入多个带参数名的参数,内部会组装为一个字典。使用**kwargs接收。

示例:

def power_value(**kwargs):
    print(type(kwargs))
    print(kwargs)

power_value(name="XiaoLi",age=20,address="china")
power_value(**{"name":"XiaoLi","age":20,"address":"china"})

允许以参数名 = 数值 的形式传值,也可以用 **dict字典 的方式传值,注意**是标识。


命名关键字参数:传值时必须加上参数名,否则python解释器会报错。这是固定参数的一种方式,一般用*标识。

示例:

def name_value(parm1,parm2,*,parm3,parm4):
    print(parm1,parm2,parm3,parm4)

name_value(parm1=1,parm2=2,parm3=3,parm4=4)
name_value(1,2,parm3=3,parm4=4)
name_value(1,2,3,4)

一般传值时参数名可加可不加,但使用命名关键字参数,*后面的参数名必须加。命名关键字参数可以设定默认值

*注意:如果命名关键字前面已经有了可变参数*args,就不用加了


可组合:这五种参数可以组合到一起使用,但顺序必须是:位置参数-->默认参数-->可变参数-->命名关键字参数-->关键字参数。

2、全局变量和局部变量

作用域:变量生效的范围。

全局变量:函数外部定义的变量,作用域是全局。

局部变量:函数内部定义的变量,作用域是函数内部。

全局变量在整个程序运行中都可以访问,但局部变量只生效于定义的那个函数中。

示例:

int_value = 20

def local_value():
    int_value1 = 30
    print(int_value1)
    print(int_value)

local_value()
print(int_value)
print(int_value1)

2.1、局部变量与全局变量同名

若函数中第一次出现变量 = 某个值,且这个变量与全局变量同名,函数调用时优先会将这个同名变量识别为局部变量,且不会对全局变量造成影响。

示例:

int_value = 20

def local_value():
    int_value = 30
    print(int_value)

local_value()
print(int_value)

但如果出现的变量没有定义(没有变量名 = 某个值),那么优先被认定为全局变量。

示例:

int_value = 20

def local_value():
    print(int_value)

local_value()
print(int_value)

如果变量既不是全局变量,也不是局部变量,编译器会报错。

它们的优先级一定是先局部,再全局。

注意:避免产生冲突,命名尽量要唯一。

2.2、改变全局变量

首先,一般情况下是不能直接改全局变量的,因为在你改的时候有一个赋值过程,这一过程会被编译器认定为定义,于是乎函数内部的全局变量被认定为局部变量,自然就报错了。

示例:

int_value = 20

def local_value():
    print(int_value)
    int_value += 2

local_value()
print(int_value)

那怎么让编译器知道这是个全局变量,且我要更改这个全局变量的值呢?

这就要用到:global。

示例:

int_value = 20

def local_value():
    global int_value
    print(int_value)
    int_value += 2
    print(int_value)

local_value()
print(int_value)

用global声明的变量会被认定为全局变量,这时我们就可以对其重新赋值了,新的值也会替换原来的值。

注意:除非不得已,一般情况下还是少用全局变量,其权限太大,容易给程序带来未知的逻辑错误。

相关推荐
Theodore_10222 小时前
4 设计模式原则之接口隔离原则
java·开发语言·设计模式·java-ee·接口隔离原则·javaee
网易独家音乐人Mike Zhou3 小时前
【卡尔曼滤波】数据预测Prediction观测器的理论推导及应用 C语言、Python实现(Kalman Filter)
c语言·python·单片机·物联网·算法·嵌入式·iot
安静读书3 小时前
Python解析视频FPS(帧率)、分辨率信息
python·opencv·音视频
----云烟----4 小时前
QT中QString类的各种使用
开发语言·qt
lsx2024064 小时前
SQL SELECT 语句:基础与进阶应用
开发语言
小二·4 小时前
java基础面试题笔记(基础篇)
java·笔记·python
开心工作室_kaic5 小时前
ssm161基于web的资源共享平台的共享与开发+jsp(论文+源码)_kaic
java·开发语言·前端
向宇it5 小时前
【unity小技巧】unity 什么是反射?反射的作用?反射的使用场景?反射的缺点?常用的反射操作?反射常见示例
开发语言·游戏·unity·c#·游戏引擎
武子康5 小时前
Java-06 深入浅出 MyBatis - 一对一模型 SqlMapConfig 与 Mapper 详细讲解测试
java·开发语言·数据仓库·sql·mybatis·springboot·springcloud
转世成为计算机大神5 小时前
易考八股文之Java中的设计模式?
java·开发语言·设计模式