Python 函数的定义与调用

简介: Python 中使用def下面这段代码定义了一个简单函数。这段代码仅仅是对函数的定义,并没有调用执行。这条定义语句运行后会新建一个名为repeator的变量名,其类型为function,即函数。与内置函数一样,定义完函数后,可以通过函数名调用执行。def repeator(s , n) : result = s * n print(result) repeator('嗷' , 3)在很多情况下,函数需要将计算的结果返回到调用处。在这类函数的函数体中,通常包含一条return。
✅作者简介:人工智能专业本科在读,喜欢计算机与编程,写博客记录自己的学习历程。
🍎个人主页: 小嗷犬的博客
🍊个人信条:为天地立心,为生民立命,为往圣继绝学,为万世开太平。
🥭本文内容:Python 函数的定义与调用

1.定义和调用函数

Python 中使用 def语句创建函数,其一般的格式如下所示:
def name(arg1, arg2, ...,argN):
    statements
下面这段代码 定义了一个简单函数。
def repeator(s, n):
    result = s * n
    print(result)
这段代码仅仅是对函数的定义,并没有调用执行。这条定义语句运行后会新建一个名为 repeator的变量名,其类型为 function,即函数。
def repeator(s, n):
    result = s * n
    print(result)
print(type(repeator))
与内置函数一样,定义完函数后,可以通过函数名 调用执行。
def repeator(s, n):
    result = s * n
    print(result)
repeator('嗷', 3)
在很多情况下,函数需要将计算的结果返回到调用处。在这类函数的函数体中,通常包含一条 return语句:
def name(arg1, arg2, ...,argN):
    statements 
    return value
在创建函数时, 没有在函数体中添加 return语句,Python 也会默默地在函数体最后添加一条 return None
def repeator(s, n):
    result = s * n
    print(result)
value = repeator('嗷', 3)
print(value)
函数如果以返回值来输出:
def repeator(s, n):
    result = s * n
    return result
print(repeator('嗷', 3))
在 Python 中, 还允许在函数中返回多个值。 只需将返回值以逗号隔开, 放在 return关键字后面即可。
def calculator(m, n): 
    return m+n, m-n, m*n, m/n
i, j = 2, 
r1, r2, r3, r4 = calculator(i, j)
print(f'{i} 和 {j} 的加减乘除运算结果是:{r1},{r2},{r3},{r4}')

在这里总结一下函数调用的四个步骤:

  1. 程序执行到函数调用时,在调用处暂停,等待函数执行完毕;
  2. 将实参赋值给函数的形参;
  3. 执行函数体中的语句;
  4. 调用结束后,回到调用前暂停处继续执行,如果函数体中执行了return语句, return关键字后的值会返回到暂停处,供程序使用,否则函数返回None值。

2.函数参数

2.1 参数传递

参数的传递过程,实际上是一个赋值的过程。在调用函数时,调用者的实际参数自动赋值给函数的形式参数变量。
def avg(m, n):
    return (m + n) /2
print(avg(5, 2))

2.2 不可变和可变类型参数

目前我们所学习的不可变类型包括:整型、浮点型、字符串和元组,可变类型有:列表、字典和集合等。这些都可以作为参数的类型。但参数在函数中使用时,这两种类型的表现有所不同。

下面的代码调用时,传递的是不可变类型的参数:

def priceChanger(p):
    p = p + 10 
    print('改变后的价格:{:.2f}'.format(p))
price = 10.8
priceChanger(price)
print(price)
在使用可变参数时,函数体中可以改变参数的元素:
def contentChanger(name_list):
    name_list[0], name_list[1] = name_list[1], name_list[0]
    print('函数中的 name_list:', name_list)
language_name = ['C', 'Python']
contentChanger(language_name)
print('调用函数后的 language_name:', language_name)
因此,在使用可变类型参数时需要特别注意,如果在函数中修改了参数的元素,这种修改会影响调用者的变量。 如果想消除这种影响,可以使用列表 copy方法或者使用分片操作创建新列表。

2.3 位置参数

位置参数是调用函数为形参赋值的一种默认方式。实参与形参按照从左到右的位置顺序依次赋值。
def myMinus(num1, num2): 
    return num1 - num2
print(myMinus(5, 2))
赋值顺序改变将得到不同的结果。
def myMinus(num1, num2): 
    return num1 - num2
print(myMinus(2, 5))

2.4 关键字参数

为了避免位置参数赋值带来的混乱,Python 允许调用函数时通过关键字参数的形式指定形参与实参的对应关系。 调用者使用 name=value的形式来指定函数中的哪个形参接受某个值:
def myMinus(num1, num2): 
    return num1 - num2
print(myMinus(num1=5, num2=2))
print(myMinus(num2=2, num1=5))

2.5 指定默认参数值

在函数定义时,可以为参数指定值。这样当函数调用者没有提供对应参数值时,就可以使用指定的默认值。 指定默认参数值在 Python 的函数中广泛存在。例如,打印函数 print,在查看其帮助时,其函数的部分描述如下:
print(...)
    print(value, ..., sep=' ', end='\n', file=sys.stdout, flush=False)
    
    Prints the values to a stream, or to sys.stdout by default.
    Optional keyword arguments:
    file:  a file-like object (stream); defaults to the current sys.stdout.
    sep:   string inserted between values, default a space.
    end:   string appended after the last value, default a newline.
    flush: whether to forcibly flush the stream.
可以看到, print函数的 sependfileflush参数都指定了默认值。
print('C', 'C++', 'Java', 'Python')
如果调用时指定了 sep参数的值,则会使用该值来连接每个打印的值。
print('C', 'C++', 'Java', 'Python', sep='_')
在定义函数时, 为形参指定默认值, 就可以让该形参在调用时变为可选:
def myMod(x, y=2): 
    return x % y
print(myMod(13,4))
print(myMod(13))

2.6 任意数量参数

Python 允许在定义函数时使用单星号 *来收集位置参数,双星号 **收集关键字参数。

2.6.1 单星号*收集位置参数

单个星号将一组可变数量的位置参数组合成参数值的元组。在函数内部可以通过访问元组中的每个元素来使用参数。
def m_value(*values):
    max_value = max(values)
    min_value = min(values)
    print(f'最大值: {max_value}, 最小值: {min_value}')
m_value(8, 6, 7, 4, 3, 9)

2.6.2 双星号**收集关键字参数

针对形参的关键字参数赋值形式, 利用 Python 定义函数时, 在形参前面加上双星号 **来定义收集关键字参数的形参。此时形参是字典类型。
def f(**info):
    if 'name' not in info.keys():
        print('必须拥有名称信息。')
    else:
        print(info['name'] + '的诞生年份:' + info.get('time', '不详'))

f(name = 'C', time = '1972')
f(name = 'Python')

2.7 解包参数

在调用函数时,实参也可以使用 ***语法。此时不是收集参数,正好相反, 实参前加上 ***执行的是参数解包。 通常来说, 在列表、元组等类型的实参值前加上 *, 将这些类型的元素解包成位置参数的形式;在字典类型的实参值前加上 **,将字典的元组解包成关键字参数的形式。

当调用者的数据存储在列表中时, 可以通过在列表前加上*对列表解包来实现位置参数形式的调用。

当调用者的数据存储在字典中时, 可以通过在字典前加上**对字典解包来实现关键字参数形式的调用。

def f(name, time = '不详'):
    if name and len(name) > 0:
        print(name + '的诞生年份:' + str(time))
    else:
        print('必须拥有名称信息。')

info1 = ['C', '1972']
f(*info1)

info2 = {'name':'Python', 'time':'1989'}
f(**info2)

目录
相关文章
|
24天前
|
开发者 Python 容器
python函数基础以及函数参数简解
python函数基础以及函数参数简解
|
1天前
|
Java Python
全网最适合入门的面向对象编程教程:50 Python函数方法与接口-接口和抽象基类
【9月更文挑战第18天】在 Python 中,虽无明确的 `interface` 关键字,但可通过约定实现类似功能。接口主要规定了需实现的方法,不提供具体实现。抽象基类(ABC)则通过 `@abstractmethod` 装饰器定义抽象方法,子类必须实现这些方法。使用抽象基类可使继承结构更清晰、规范,并确保子类遵循指定的方法实现。然而,其使用应根据实际需求决定,避免过度设计导致代码复杂。
|
4天前
|
Python
全网最适合入门的面向对象编程教程:Python函数方法与接口-函数与方法的区别和lamda匿名函数
【9月更文挑战第15天】在 Python 中,函数与方法有所区别:函数是独立的代码块,可通过函数名直接调用,不依赖特定类或对象;方法则是与类或对象关联的函数,通常在类内部定义并通过对象调用。Lambda 函数是一种简洁的匿名函数定义方式,常用于简单的操作或作为其他函数的参数。根据需求,可选择使用函数、方法或 lambda 函数来实现代码逻辑。
|
17天前
|
Python
python 函数
【9月更文挑战第4天】python 函数
36 5
WK
|
24天前
|
Python
python中的函数有哪些种类?
在 Python 中,函数根据定义方式、用途及来源可分为多种类型:自带的内置函数(如 print(), len())无需导入直接使用;标准库函数需导入相应模块后使用;第三方库函数则需先安装库再导入使用;用户自定义函数可根据需求定义并多次调用;匿名函数(lambda)无函数名,常用于需要函数对象但不想单独定义的情形;高阶函数接受或返回函数;装饰器函数可在不改动原函数代码情况下为其添加新功能;生成器函数使用 yield 逐个返回值;递归函数在自身定义中调用自身;嵌套函数在一个函数内定义,可访问外部函数变量。各种函数类型在编程中有不同的用途和优势。
WK
39 12
|
22天前
|
数据安全/隐私保护 开发者 Python
在 Python 中定义封装?
【8月更文挑战第29天】
23 8
|
22天前
|
Python
Python 中 help() 和 dir() 函数的用法
【8月更文挑战第29天】
19 5
|
23天前
|
Python
12类常用的Python函数
12类常用的Python函数
|
21天前
|
存储 程序员 Python
Python类的定义_类和对象的关系_对象的内存模型
通过类的定义来创建对象,我们可以应用面向对象编程(OOP)的原则,例如封装、继承和多态,这些原则帮助程序员构建可复用的代码和模块化的系统。Python语言支持这样的OOP特性,使其成为强大而灵活的编程语言,适用于各种软件开发项目。
16 1
|
24天前
|
Python
python中getattr函数 hasattr函数
python中getattr函数 hasattr函数