python编程:(七)函数

admin 2021年03月28日 584次浏览

1、函数

1.1、定义

  • 函数用于封装一个特定的功能,表示一个功能或者行为
  • 函数是可以重复执行的语句块, 可以重复调用

1.2、作用

提高代码的可重用性和可维护性(代码层次结构更清晰)

1.3、定义函数

  • 语法:
  def 函数名(形式参数):
      函数体
  • 说明:

    • def 关键字:全称是define,意为”定义”
    • 函数名:对函数体中语句的描述,规则与变量名相同
    • 形式参数:方法定义者要求调用者提供的信息
    • 函数体:完成该功能的语句
    • 函数的第一行语句建议使用文档字符串描述函数的功能与参数
  • 示例

    # 定义一个行列转换函数
    def row_col_recover(list):
        """
        获取 list 中的数据进行行列转换\n
        :param list: 需要转换的数据列表
        :return:返回转换后的数据
        """
        temp = []
        for c in range(len(list[0])):
            temp.append([])
            for r in range(len(list)):
                temp[c].append(list[r][c])
        return temp
    

1.4、调用函数

  • 语法

    • 函数名()

    • 变量 = 函数名(实际参数)

  • 说明
    根据形参传递内容

  • 示例

    # 没有返回值函数调用
    row_col_recover()
    
    # 有返回值函数调用
    recover_list = row_col_recover(list)
    

1.5、返回值

  • 定义
    方法定义者告诉调用者的结果
  • 语法:
    return 数据
  • 作用
    • 返回数据
    • 退出函数
  • 说明
    • return后没有语句,相当于返回 None
    • 函数体没有return,相当于返回 None

1.6、可变/不可变类型在传参时的区别

  • 不可变类型参数有
    • 数值型(整数,浮点数,复数)
    • 布尔值( bool)
    • 空值 (None )
    • 字符串 (str)
    • 元组 (tuple)
    • 固定集合 (frozenset)
  • 可变类型参数有
    • 列表 (list)
    • 字典 (dict)
    • 集合 (set)
  • 传参说明
    • 不可变类型的数据传参时,函数内部不会改变原数据的值
    • 可变类型的数据传参时,函数内部可以改变原数据, 函数执行过后,不用通过返回值也能拿到修改后的结果

1.7、函数参数

1.7.1、实参传递方式(argument)

  • 位置传参
    实参与形参的位置依次对应

  • 序列传参
    实参用*将序列拆解后与形参的位置依次对应

  • 关键字传参
    实参根据形参的名字进行对应

  • 字典关键字传参

    • 定义
      实参用**将字典拆解后与形参的名字进行对应
    • 作用:
      配合形参的缺省参数,可以使调用者随意传参
  • 示例

    def fun01(a, b, c):
        print(a)
        print(b)
        print(c)
    
    # 位置实参:实参根据位置与形参进行对应
    fun01(1, 2, 3)
    
    # 序列实参:使用星号将序列中的元素拆开,与形参进行对应
    # 序列:字符串、列表、元组
    list01 = ["aaa", "bb", "cc"]
    fun01(*list01)
    
    # 关键字实参:实参根据名称与形参进行对应
    fun01(b=2, a=1, c=3)
    
    # 字典实参:使用双星号将字典中的元素拆开,根据“键”与形参进行对应,传递值
    dict01 = {"c": 33, "a": 11, "b": 22}
    fun01(**dict01)
    

1.7.2、形参定义方式(parameter)

  • 缺省参数

    • 语法
          def 函数名(形参名1=默认实参1, 形参名2=默认实参2, ...):
              函数体
    
    • 说明
      • 缺省参数必须自右向左依次存在,如果一个参数有缺省参数,则其右侧的所有参数都必须有缺省参数
      • 缺省参数可以有0个或多个,甚至全部都有缺省参数
  • 位置形参

    • 语法
      def 函数名(形参名1, 形参名2, ...):
          函数体
    
  • 星号元组形参

    • 语法
      def 函数名(*元组形参名):
        函数体
    
    • 作用
      收集多余的位置传参
    • 说明
      • 一般命名为'args'
      • 形参列表中最多只能有一个
  • 命名关键字形参

    • 语法
      def 函数名(\*, 命名关键字形参1, 命名关键字形参2, ...):
          函数体
    
      def 函数名(\*args, 命名关键字形参1, 命名关键字形参2, ...):
          函数体
    
    • 作用
      强制实参使用关键字传参
  • 双星号字典形参

    • 语法
      def 函数名(\*\*字典形参名):
          函数体
    
    • 作用:
      收集多余的关键字传参
    • 说明:
      • 一般命名为'kwargs'
      • 形参列表中最多只能有一个
  • 参数自左向右的顺序
    位置形参 --> 星号元组形参 --> 命名关键字形参 --> 双星号字典形参

  • 示例

    # 默认形参:实参可以不传递数据(从右向左依次存在)
    def fun01(a=0, b="bb", c=1.5):
        print(a)
        print(b)
        print(c)
    
    fun01()
    fun01(1, "b")
    
    
    # 位置形参:实参根据位置与形参进行对应
    def fun01(a,b,c):
        print(a)
        print(b)
        print(c)
    
    fun01(1,2,3)
    
    
    # 星号元组形参:让位置实参的数量无限
    def fun02(p1, p2, *args):
        print(args)
    
    fun02(1, 2)
    fun02(1, 2, 3)
    fun02(1, 2, 3, 4, 5)
    
    
    # 命名关键字形参:传递的实参必须是关键字实参
    ## 写法1:星号元组形参以后的参数是命名关键字形参
    def fun03(*args, p1="", p2):
        print(args)
        print(p1)
        print(p2)
    
    fun03(2, 2, p1=111, p2=222)
    fun03(p1=111, p2=222)
    fun03(p2=222)
    
    ## 写法2:星号以后的位置形参是命名关键字形参
    def fun04(*, p1=0, p2):
        print(p1, p2)
    
    fun04(p1=1, p2=2)
    fun04(p2=2)
    
    
    # 双星号字典形参:让关键字实参的数量无限
    def fun05(**kwargs):
        print(kwargs)
    
    fun05(a=1)  # 相当于{'a': 1}
    fun05(a=1, b=2)
    fun05(a=1, b=2, c=3)  # 相当于{'a': 1, 'b': 2, 'c': 3}
    

2、作用域LEGB

  • 作用域:变量起作用的范围
  • Local局部作用域:函数内部,函数内部的变量称为局部变量
  • Enclosing外部嵌套作用域 :函数嵌套
  • Global全局作用域:模块(.py文件)内部
  • Builtin内置模块作用域:builtins.py文件

2.1、变量名的查找规则

  • 由内到外:L -> E -> G -> B
  • 在访问变量时,先查找本地变量,然后是包裹此函数外部的函数内部的变量,之后是全局变量,最后是内置变量

2.2、局部变量

  • 定义在函数内部的变量(形参也是局部变量)
  • 只能在函数内部使用
  • 调用函数时才被创建,函数结束后自动销毁

2.3、全局变量

  • 定义在函数外部,模块内部的变量
  • 在整个模块(py文件)范围内访问(但函数内不能将其直接赋值)

2.4、global 语句

  • 作用
    • 在函数内部修改全局变量
    • 在函数内部定义全局变量(全局声明)
  • 语法
    global 变量1, 变量2, …
  • 说明
    • 在函数内直接为全局变量赋值,视为创建新的局部变量
    • 不能先声明局部的变量,再用global声明为全局变量

2.5、nonlocal 语句

  • 作用
    在内层函数修改外层嵌套函数内的变量
  • 语法
    nonlocal 变量名1,变量名2, ...
  • 说明
    在被嵌套的内函数中进行使用