【Python学习002】函数参数

news/2023/5/28 8:55:13

【Python学习002】函数参数

概述

函数是组织好的、可重复使用的,用来实现单一,或相关联功能的代码段。函数能提高应用的模块性,和代码的重复利用率。

Python提供了许多内建函数,比如print()sum,但是有些时候基础函数并不能实现想要的业务功能,所以必须要自定义函数,函数的使用必须遵循“先定义,后调用”的原则。函数的定义就相当于事先将内存地址赋值给定义的函数名,函数名就是对这段代码的引用,这类似于变量的定义,在Python中一个函数其实是一个【function】对象或者【method】对象(取决于函数是隶属于一个类还是单独存在)。

def add(a: int, b: int) -> int:"""return a+b:param a: 参数1,整形,加数1:param b: 参数2,整形,加数2:return: a+b"""return a + b

上面就是Python函数的一个例子,这段代码主要包括:

  1. 【def】关键字;
  2. 函数名称;
  3. 函数文档描述;
  4. 函数参数和注解;
  5. 函数体;
  6. 函数返回值和注解;

函数参数

函数的参数分为形式参数和实际参数,简称形参和实参。

  • 形参即在定义函数时,括号内声明的参数。形参本质就是一个变量名、一个引用,用来接收外部传来的值;
  • 实参即在调用函数时,括号内传入的值,值可以是常量、变量、表达式或三者的组合。

在Python中,变量名与值只是单纯的绑定关系,而对于函数来说,这种绑定关系只在函数调用时生效,在调用结束后解除。

位置参数

位置参数也称必须参数,位置参数须以从左到右的顺序传入函数。调用时的数量必须和声明时的一样。

def add(a: int, b: int) -> int:"""return a+b:param a: 参数1,整形,加数1:param b: 参数2,整形,加数2:return: a+b"""return a + badd(1, 2)

在上面那个例子汇总,【a】和【b】就是位置参数,add(1, 2)就是将a和1绑定,b和2绑定。

关键字参数

在调用函数时,实参可以是key=value的形式,称为关键字参数。凡是按照这种形式定义的实参,可以不按照从左到右的顺序定义,但仍能进行形参和实参的绑定。使用该方式传递(绑定)参数的时候有两点需要注意:

  1. 不可以对一个形参重复赋值;
  2. 关键字参数在位置参数后面,因为python函数在解析参数时,是按照顺序来的,位置参数是必须先满足,才考虑其他可变参数。
def add(a: int, b: int) -> int:"""return a+b:param a: 参数1,整形,加数1:param b: 参数2,整形,加数2:return: a+b"""return a + badd(1, 2) -> 3
add(a=1, b=2) -> 3
add(b=2, a=1) -> 3
add(1, b=2) -> 3
add(2, a=1) -> add() got multiple values for argument 'a'
add(a=1, 2) -> positional argument follows keyword argument

默认参数

在定义函数时,就已经为形参赋值,这类形参称之为默认参数(缺省参数)。当一个函数拥有多个参数且函数不可重构的时候默认参数将会十分有效,可以将值经常改变的参数定义成位置参数,将值改变较少的参数定义成默认参数,从而降低函数调用的复杂度。

def add(a: int, b: int=2) -> int:"""return a+b:param a: 参数1,整形,加数1:param b: 参数2,整形,加数2:return: a+b"""return a + badd(1) -> 3
add(1, 3) -> 4

在上面那个例子中,【b】就是一个默认参数,使用默认参数有几点注意事项:

  1. 默认参数必须在位置参数之后;

  2. 默认参数的值仅在函数定义阶段被赋值一次;

  3. 默认参数的值通常应设为不可变类型

动态参数

顾名思义,动态参数就是传入的参数的个数是动态的,可以是1个、2个到任意个,还可以是0个。在不需要的时候,你完全可以忽略动态函数,不用给它传递任何值。

在Python中,动态参数有两种分别是*args**kwargs,二者的区别在于星号的数量,前者会被处理成一个元祖,而后者会被处理成一个字典。

def func_tuple(*args: Tuple[Any]) -> None:print(args)def func_dict(**kwargs: Mapping[Any, Any]) -> None:print(kwargs)my_dict = {1:'a', 2:'b', 3:'c'}
my_str_dict = {'1':'a', '2':1, "3":3.5, '4': [1, 2, 3]}
my_tuple = (1, 2, 3, 4)func_tuple(1, 'a', 3.5, [1, 2, 3]) -> (1, 'a', 3.5, [1, 2, 3])
func_tuple(*my_tuple) -> (1, 2, 3, 4)
func_dict(my_dict) -> func_dict() takes 0 positional arguments but 1 was given
func_dict(**my_dict) -> func_dict() keywords must be strings
func_dict(**my_str_dict) -> {'1': 'a', '2': 1, '3': 3.5, '4': [1, 2, 3]}
func_dict(a=1, b=2, c=3) -> {'a': 1, 'b': 2, 'c': 3}

func_dict(my_dict)报错的原因在于解析器将【my_dict】当做一个位置参数进行传递,而函数本身没有位置参数,所以报错了,正确的做法是使用**对字典进行解包或者实参从左到右都是关键字参数的形式传递(字典解包还需要注意他的键必须是字符类型)。如果想要对元祖解包,需要使用*号。

限定位置形参

也称强制位置参数,在Python3.8之后被引入,被定义为限定位置形参的参数必须放在形参表的最前面,并在后面使用斜杠【/】(独占一个参数位)与普通形参分隔,比如下面这样:

def func(a, b, /, c, d) -> None:print(a + b + c + d)func(1, 2, 3, 4) -> 10
func(1, b=2, c=3, d=4) -> TypeError: func() got some positional-only arguments passed as keyword arguments: 'b'

其中【a】、【b】是限定位置形参,只能按照位置参数的形式进行传递,而【c】和【d】仍然是普通形参,可以接受位置参数关键字参数两种形式传递。

限定关键字形参

也称命名关键字参数,和限定位置形参的目的一样,就是为了限定参数只能以关键字参数的形式进行传递,使用它的好处在于可以显式地指明参数含义,有利于可读性,同时强制使用关键字参数的形式也有利于保证版本兼容。被定义为限定关键字形参的参数需要放在形参表的后面,并在前面使用星号【*】(独占一个参数位)与普通形参分隔,示例如下:

def func(a, b, *, c, d) -> None:print(a + b + c + d)func(1, 2, c=3, d=4) -> 10
func(1, 2, 3, 4) -> TypeError: func() takes 2 positional arguments but 4 were given

其中【c】和【d】是限定关键字形参,【a】、【b】仍然是普通形参。

综合示例

为了进一步了解参数的各个类型,我们可以使用inspect.signature来获取函数对象(function)的相关属性和定义,示例如下:

def show_func_detail(sig):for name, param in sig.parameters.items():print('参数类型:%s, 参数名:%s, 参数默认值:%s' % (param.kind, name, param.default))def func1(a, b, c, d):passdef func2(a, b, c=3, d='default'):passdef func3(*args):passdef func4(**kwargs):passdef func5(a, b, /, c, d):passdef func6(a, b, *, c, d):passsig1 = signature(func1)
sig2 = signature(func2)
sig3 = signature(func3)
sig4 = signature(func4)
sig5 = signature(func5)
sig6 = signature(func6)show_func_detail(sig1)
show_func_detail(sig2)
show_func_detail(sig3)
show_func_detail(sig4)
show_func_detail(sig5)
show_func_detail(sig6)----------------------------------------------------------------------------
参数类型:POSITIONAL_OR_KEYWORD, 参数名:a, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:b, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:c, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:d, 参数默认值:<class 'inspect._empty'>
----------------------------------------------------------------------------
参数类型:POSITIONAL_OR_KEYWORD, 参数名:a, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:b, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:c, 参数默认值:3
参数类型:POSITIONAL_OR_KEYWORD, 参数名:d, 参数默认值:default
----------------------------------------------------------------------------
参数类型:VAR_POSITIONAL, 参数名:args, 参数默认值:<class 'inspect._empty'>
----------------------------------------------------------------------------
参数类型:VAR_KEYWORD, 参数名:kwargs, 参数默认值:<class 'inspect._empty'>
----------------------------------------------------------------------------
参数类型:POSITIONAL_ONLY, 参数名:a, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_ONLY, 参数名:b, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:c, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:d, 参数默认值:<class 'inspect._empty'>
----------------------------------------------------------------------------
参数类型:POSITIONAL_OR_KEYWORD, 参数名:a, 参数默认值:<class 'inspect._empty'>
参数类型:POSITIONAL_OR_KEYWORD, 参数名:b, 参数默认值:<class 'inspect._empty'>
参数类型:KEYWORD_ONLY, 参数名:c, 参数默认值:<class 'inspect._empty'>
参数类型:KEYWORD_ONLY, 参数名:d, 参数默认值:<class 'inspect._empty'>

从上面的示例可以看到:

  1. 普通形参:POSITIONAL_OR_KEYWORD;
  2. 默认参数只是更改了参数的默认值,不更改它的类型;
  3. 动态参数:VAR_POSITIONAL或者VAR_KEYWORD;
  4. 限定位置形参:POSITIONAL_ONLY;
  5. 限定关键字形参:KEYWORD_ONLY。

总结

  1. 函数形参只是绑定关系;
  2. 普通的函数形参可以接受两种形式(位置参数形式和关键字参数形式),每个都有自己的注意事项;
  3. 如果函数接受多个参数,可以给函数赋予默认值(最好是不可变类型);
  4. 如果不确定传入参数的数量使用动态参数;
  5. 合理的使用限定位置形参和限定关键字形参可以有效提升代码的可读性;

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.exyb.cn/news/show-4555014.html

如若内容造成侵权/违法违规/事实不符,请联系郑州代理记账网进行投诉反馈,一经查实,立即删除!

相关文章

5.JAVA基础入门必备

文章目录前言一、数据类型二、标识符三、键盘录入四、IDEA中的第一个代码五、IDEA中的设置六、IDEA的项目和模块操作总结前言 一、数据类型 重点记忆byte的取值范围!! 不同类型数据的打印: public class VariableDemo3{//主入口public static void main(String[] args){//byt…

JD分析

1.负责城市大了基础产品云服务测试工作&#xff1b; 解说就是保证基础测试工作&#xff0c;是测试主要责任&#xff0c;测试经理这个角色&#xff0c;是带来领测试人员进行测试。 2.测试经理可以分配测试开发人员进行测试工具的开发。这个职位还要负责开发。 3.搭建明细是进…

jd是什么职位(Jd是什么职位的简称)

前端开发工程师jd jd是什么意思 就是说职位描述……前端工程师职位描述如下的意思、 JD是Juris Doctor等其他意思的缩写。Job Description的缩写&#xff0c;就是职位描述&#xff1b; 你这里就是前端工程师职位描述如下的意思junior developer 高级软件开发工程师 “JD”在招聘…

jd什么意思(职位jd什么意思)

JD是什么意思&#xff1f; 招聘的话JD有两种解释&#xff1a; 1、就是岗位介绍、和工作职责描述的意思&#xff1b; 2、就是法学博士的简写。一般在招聘中&#xff0c;最长用到的意思就是岗位介绍和工作职责描述的意思。 职位描述又叫职位界定&#xff0c;其成果叫工作说明书(j…

我研究了一个月阿里的岗位JD,不曾想.....

很多人都在纠结面试要准备什么&#xff0c;当然是要具体岗位具体对待了&#xff01;如果你现在还没有想好到底要面什么的公司&#xff0c;具体哪个职位的话&#xff0c;那就先把大多数公司会考的技术点搞清楚&#xff5e;我最近研究了一下各大厂&#xff08;阿里、腾讯、百度、…

Python爬取实习僧算法JD

之前做了一个爬虫给自己的CSDN刷量&#xff0c;其实跟写一个简单的小爬虫差不多。在公司里&#xff0c;爬虫一般都跟nlp相关的业务息息相关&#xff0c;这次先爬取一下实习僧网站上的算法JD&#xff0c;为以后学习nlp相关的知识准备一下数据。 先在实习僧上搜索算法岗位&#…

测试开发序列春招JD

美团 截止日期 2020.02.22 -tag 简历稀缺 岗位职责 如果你耐心、细心&#xff0c;喜欢玩大家来找茬&#xff1b; 如果你对技术有着各种吹毛求疵的见解和发现&#xff1b; 在这里&#xff0c;你可以尽情尝鲜&#xff0c;在第一时间发现各种BUG&#xff1b; 在这里&#xff0c;你…

【今日CV 计算机视觉论文速览 第112期】Mon, 6 May 2019

今日CS.CV 计算机视觉论文速览 Mon, 6 May 2019 Totally 31 papers ?上期速览✈更多精彩请移步主页 Interesting: ?HDR图像超分辨联合算法, 通过重建高频细节信息、来共同进行图像超分辨和高动态范围重建。高频部分只在反射部分&#xff08;基于retinex的图像解构&#xff0…

〖金融帝国实验室〗(Capitalism Lab)v8.2.00官方重大版本更新(2023.01.17正式发布)

〖金融帝国实验室〗&#xff08;CapLab&#xff09;v8.2.00正式发布&#xff01; ————————————— ※v8.2.00更新内容摘要&#xff1a; 1.新增生活服务业&#xff1a;快餐店、比萨店、蛋糕店和咖啡店。 2.可以通过在农场周围购买土地并耕耘来实现产能扩容。 3.…

分库分表实战案例

一、 二、 分库分表实战案例 分表 垂直分表水平拆分 分库 垂直水平 分片规则 基于范围分片 时间&#xff1a; 按照年、月、日去切分。例如order_2020、order_202005、order_20200501 地域&#xff1a; 按照省或市去切分。例如order_beijing、order_shanghai、order_chen…

年末阿里百度等大厂技术面试题汇总,深夜思考

前言 相信前几天在朋友圈晒无聊的小伙伴们&#xff0c;也陆续结束了假期。很多公司为了员工的健康考虑&#xff0c;启动了远程办公模式。 床在桌边&#xff0c;饭在桌上&#xff0c;家里一切都那么安逸&#xff0c;专心工作真的是一件难事。远程工作最大的敌人就是&#xff1…

车载以太网 - 车辆信息和车辆声明 - 09

到今天这一篇,对于ISO 13400 - 2的DoIP协议介绍就完事了,对DoIP协议的规范介绍基本已经全部包括了,无论是我们作为软件开发人员还是测试人员,了解这部分内容基本就能够满足这块基础的开发要求,大家如果在研究或者学习这块内容的时候有什么问题欢迎私聊;并且在本篇文章结束…

关于爬虫反爬机制处理方法(整合)

常见得反爬机制及解决办法 1、针对请求头做出得反爬 简介&#xff1a;网站通过去检查headers中的User-Agent字段来反爬&#xff0c;如果我们没有设置请求头&#xff0c;那么headers默认是python这样就会出现访问失败、没有权限等原因&#xff0c;如果去伪造一个请求头是可以避…

【python爬虫专项(27)】拉勾网数据采集(关键词网址不发生变化)

拉勾网登陆后&#xff0c;选择某城市&#xff0c;搜索任意关键字&#xff0c;采集岗位信息数据 起始参考网址&#xff1a;全国数据分析岗位招聘 前一篇是搜索关键词网址发生变化的情况&#xff0c;接下来就处理搜索关键词不发生变化情况下的数据爬取&#xff0c;就以上一篇提…

什么样的人才能做互联网产品经理【爬取拉勾网招聘信息】

分析目的 在这个校招如火如荼的季节&#xff0c;相信大家对各种招聘网站已经再熟&#xff08;yan&#xff09;悉&#xff08;fan&#xff09;不过了&#xff0c;各种java开发、算法、前端、后端岗位真的是琳琅满目&#xff0c;而我觉得其中与我的个人兴趣和专业匹配度最高的就…

上线云导播台

前面是PVW信号面板的媒体流&#xff0c;以前做过桌面系统导播台&#xff0c; 后来公司需要开发一个云导播台&#xff0c;所以做了一版&#xff0c;为了降低前端开发难度&#xff0c;就直接把前端操作全部封装在一路流中&#xff0c;这个思路也是参考七牛云导播台的方式&#xf…

阿里云视频点播配置及使用HTML5页面播放

2019独角兽企业重金招聘Python工程师标准>>> 最近公司要使用阿里云视频点播&#xff0c;实现手机端使用WAP进行视频播放。在这里将配置过程记录一下&#xff0c;以供日后参考。 1、初始化向导 视频访问域名 绑定CNAME 2、全局设置 转码设置 系统默认的对我来说已经足…

VMware Cloud Director 严重漏洞可使整个云基础设施遭接管

聚焦源代码安全&#xff0c;网罗国内外最新资讯&#xff01;编译&#xff1a;代码卫士上周四&#xff0c;VMWare 公司发布更新&#xff0c;修复了位于 Cloud Director 产品中的一个严重漏洞 (CVE-2022-22966)&#xff0c;它可被用于发动远程代码执行攻击。该漏洞评分为9.1&…

个人对粗糙集的一些理解和简单举例

文章目录1、 数据价值密度低的解决方案1.1 粗糙集中对应的概念&#xff1a;属性约简1.2 属性约简的好处1.3 粗糙集的应用2、粗糙集的简介--->原理2.1 粗糙集的概念2.2 从例子看粗糙集2.3 粗糙集模型的分类及其评估标准3、粗糙集的主要研究方向3.1 模型创新3.2 属性约简3.3 提…

Linux 父进程需要创建3个子进程,但不创建孙子进程

Linux 进程家族树 生成三个子进程不生成孙子进程1. 要求2. 分析2.1 getpid、getppid2.2 不让子进程再生成进程3. 代码4. 运行截图5. 绘制进程家族树1. 要求 如果父进程需要创建3 子进程&#xff0c;但不创建孙子进程。请编写程序&#xff0c;并画出进程家族树。 &#xff08;进…