zoukankan      html  css  js  c++  java
  • 函数介绍、函数参数

    一、函数的介绍

    1、函数是什么

    想象生活中的例子,修理工需要实现准备好工具箱里面放好锤子,扳手,钳子等工具,然后遇到锤钉子的场景,拿来锤子用就可以,而无需临时再制造一把锤子。

    修理工=>程序员
    具备某一功能的工具
    =>函数

    要想使用工具,需要事先准备好,然后拿来就用且可以重复使用
    要想用函数,需要先定义,再使用

    ps:函数就是盛放代码的容器
    
    2、为何要用函数

    为了解决下述问题:

    1)代码的组织结构不清晰,可读性差
    2)遇到重复的功能只能重复编写实现代码,代码冗余
    3)功能需要扩展时,需要找出所有实现该功能的地方修改之,无法统一管理且维护难度极大 
    
    3、如何用函数

    3.1、定义的语法

    #语法
    def 函数名(参数1,参数2,参数3,...):
        '''注释'''
        函数体
        return 返回的值
     调用的语法
    #函数名要能反映其意义
    

    3.2、定义函数

    发生的事情
    1)申请内存空间把函数体代码放进去
    2)将函数内存地址绑定给函数名
    强调:定义函数只检测语法,不执行代码。也就说,语法错误在函数定义阶段就会检测出来,而代码的逻辑错误只有在执行时才会知道
    

    3.3、函数的调用

    发生的事情:
    1)先通过函数名定位到函数的内存地址
    2)函数内存地址()->触发函数体代码的运行
    强调:调用函数才会执行函数体代码
    
    例1:
    def func():
    	print(11111      #False 语法错误
    
    例2:
    def func():
        print(1111)
        x
        print(2222)
    func()          # False 逻辑错误 
    
    例3
    def bar():
    	print('from bar')
    def foo():
    	print('from foo')
    	bar()
    foo()
        =================
    def foo():
        print('from foo')
        bar()
    def bar():
    	print('from bar')
    foo()                            #Fales 反了,要先定义,再调用
    

    3.4、定义函数的三种形式

    1. 无参:应用场景仅仅只是执行一些操作,比如与用户交互,打印
    def say():
        print('========')
        print('welcome to here')     
        print('========')
    say()
    
    def login():
        inp_name = input("username>>>: ").strip()
        inp_pwd = input("password>>>: ").strip()
        if inp_name == "egon" and inp_pwd == "123":	
    		print('login successful')
        else:
        	print("username or password error")
    login()
    
    1. 有参:需要根据外部传进来的参数,才能执行相应的逻辑,比如统计长度,求最大值最小值
    def max2(x,y)     
    	if x > y:        
    		print(x)
        else:
        	print(y)
    max2(10,20)
    
    1. 空函数:设计代码结构
    def login():
    	pass
    
    结论:

    定义时无参,意味着调用时也无需传入参数

    定义时有参,意味着调用时则必须传入参数

    3.5、调用函数的三种形式

    1)语句形式

    len('hello')    /     foo( )
    
    1. 表达式形式
    res=len('hello')*10
    print(res)
    
    1. 可以当做参数传给另外一个函数
    print(len("hello"))
    

    二、函数参数

    总体分为两大类:

    • 形参:在函数定义阶段括号内指定的参数,称之为形式参数,简称形参-》变量名

    • 实参:在函数调用阶段括号内传入的值,称之为实际参数,简称实参-》变量的值

    形参与实参的关系是:在调用函数时,实参值会绑定给形参名,在函数调用完毕后解除绑定
    

    形参系列-----

    1、位置形参:在定义函数时,按照从左到右的顺序依次定义的变量名,称之为位置形参

    ​ 特点:每次调用,必须被赋值

    def func(name,age):
        print(name)
    	print(age)
    func(1,2)
    

    2、默认形参:在定义函数时,就已经为某个形参赋值了,称之为默认形参

    ​ 特点:调用函数时,可以不用为其赋值

    def func(name,age=18):
    	print(name)
        print(age)
    func("egon")
    func("egon",19)  #  19  以调用的为准
    

    & 注意 : 可以混用位置形参与默认形参,但是

    ​ 1)、位置形参必须在前面

    ​ 2)、默认形参的值通常应该是不可变类型

    ​ 3)、默认形参的值是在函数定义阶段赋值的

    def func(name,hobby,hobbies = None):    
    	if hobbies is None:       
    		hobbies = []   
    	hobbies.append(hobby)   
    	print('%s的爱好是%s' %(name,hobbies))
    func('egon','read')
    func('tom','play')
    func('jack','music')
    func('lili','eat',["movie"])
    
    m=1111
    def func(x,y,z=m):  
        print(x)    
        print(y)   
        print(z)
        m=666
    func(1,2)      #   m仍然是1111,以先定义的为准
    

    实参系列-----

    1、位置实参:在调用函数时,按照从左到右的顺序依次传入的值,称之为位置实参

    ​ 特点:按照位置为形参赋值,一 一对应

    def res(name,age)
    	...
    res('egon',18)
    

    2、关键字实参:在调用函数时,按照key=value的形式传值,称之为关键字实参

    ​ 特点:可以打乱顺序,但是仍然能够指定道姓地为指定的形参赋值

    def res(name,age)
    	...
    res(age=18,name="egon")
    

    & 注意:可以混用位置实参与关键字实参,但是

    ​ 1)、位置实参必须在关键字实参的前面

    ​ 2)、不能为同一形参重复赋值

    def res(name,age)
    	...
    func("egon",age=18)   # True
    func(age=18,"egon")   # 语法错误
    
    def foo(x,y,z):
    	pass
    foo(1,y=2,3)   # 错误
    foo(1,y=2,z=3,x=4)  # 错误,不能重复调用
    

    可变长系列-----

    可变长参数指的是在调用函数时,传入的实参个数不固定,对应着必须有特殊形式的形参来接收溢出的实参

    实参无非两种形式======>

    ​ 溢出的位置实参--->*

    ​ 溢出的位置关键字实参--->**

    一.. ==============*与**在形参中是一种汇总行为=====================
    

    1、*在形参中的应用: *会将溢出的位置实参合并成一个元组,然后赋值给紧跟其后的那个形参

    def func(x,*args):     # y = (2,3,4,5) 
    	print(x)    
    	print(args)
    func(1,2,3,4,5)
    
    def my_sum(*args):  
    	res = 0  
        for i in args:       
        	res += i   
            print(res)
    my_sum(1,2)         结果为 1+2=3
    

    2、2个* . 在形参中的应用:* *会将溢出的关键字实参合并成一个字典,然后赋值给紧跟其后的那个形参名

    def func(x,**kwargs):      # kwargs = {"a":2,"c":4,"b":3}
        print(x)
        print(kwargs)
    func(1,a=2,b=3,c=4)
    
    二 ..==============*与**在实参中是一种打散行为=====================
    
    1、*在实参中的应用:*后可以跟可以被for循环遍历的任意类型,*会将紧跟其后的那个值打散成位置实参
    
    def func(x,y,z):   
        print(x)    
        print(y)    
        print(z)
    func(*[11,22,33])    # 11,22,33
    func(*"hel")         #  h,e,l
    unc(*{"x":111,"y":2222,"z":3333})         #     x,y,z  
    
    2、**在实参中的应用:**只能跟字典类型,**会将字典打散成关键字实参
    
    def func(x,y,z):   
        print(x)    
        print(y)   
        print(z)
    func(**{"x":111,"y":2222,"z":3333})  
    
    def index(x,y,z):
    	print(x,y,z)
    def wrapper(*args,**kwargs):  # args=(1,2,3,4,5,6)  kwargs={"a":1,"b":2,"c":3}#     		index(*args,**kwargs)  # index(*(1,2,3,4,5,6),**{"a":1,"b":2,"c":3})#     #                        index(1,2,3,4,5,6,a=1,b=2,c=3)# 
    wrapper(1,2,3,4,5,6,a=1,b=2,c=3)
    wrapper(1,y=2,z=3)
    
     了解(**):命名关键字形参: 在*与**中间的形参称之为命名关键字形参    
     特点: 必须按照key=value的形式传值
     def func(x,m=333,*args,y=222,z,**kwargs):   
         print(x)  
         print(args)    
         print(y)    
         print(z)   
         print(kwargs)
     func(1,2,3,z=4,a=1,b=2,c=3)
    

    补充:函数的返回值
    return是函数结束的标志,即函数体代码一旦运行到return会立刻终止函数的运行,并且会将return后面的值当做本次运行的结果返回
    01.返回None,函数体内没有return
    02.返回一个值:return值
    03.返回多个值:用逗号分隔开多个值,会被return返回成元组
    无return->None
    return 1个值->返回1个值
    return 逗号分隔多个值->元组

    什么时候该有返回值?
        调用函数,经过一系列的操作,最后要拿到一个明确的结果,则必须要有返回值
        通常有参函数需要有返回值,输入参数,经过计算,得到一个最终的结果
    什么时候不需要有返回值?
        调用函数,仅仅只是执行一系列的操作,最后不需要得到什么结果,则无需有返回值
        通常无参函数不需要有返回值
    
  • 相关阅读:
    [PHP] php调用不存在的方法会自动调用 __call 魔术方法
    [PHP] laravel框架响应json信息中文禁止unicode编码
    [PHP] php中的trait代码复用方式
    [nginx] 解决:upstream timed out (110: Connection timed out) while reading response header from upstream
    [linux] Linux下格式化JSON程序-jq
    [git] Git Clean 清除 untrack 没有加入版本库的文件
    goland终端如何导入github上的包
    calico 配置 BGP Route Reflectors
    改善 Kubernetes 上的 JVM 预热问题
    golang开源对象存储
  • 原文地址:https://www.cnblogs.com/caodan01/p/14201917.html
Copyright © 2011-2022 走看看