在python中,用默认参数(list,set,dict...)时要小心

在我们平时写需求的时候,如果没有了解到以下知识点,可能会出现这样的问题,掉进坑里面,甚至很难找到问题的根源。
下面我们来看看使用可变默认参数(Mutable default arguments)时会出现什么诡异的情况。
你可能写了以下函数,它有一个默认参数是一个list:
def append_to(element, to=[]):
to.append(element)
return to
然后调用该函数:
my_list = append_to(12)
print(my_list) my_other_list = append_to(42)
print(my_other_list)
每次调用该函数,如果第二个参数没有提供(使用默认参数),一个新的list将会生成,所以输出应该是:
[12]
[42]
但是,结果并非上面那样,而是下面这样:
[12]
[12, 42]
当该函数被定义时,一次性生成一个list作为默认参数,后面每次成功调用都是使用的第一次生成的那个list。
Python的默认参数只在函数被定义时生成一次,而非每次调用时生成。这就意味着如果你使用可变默认参数并改变它,所有调用该函数的结果都是这个可变对象。
正确的做法应该是:
让默认参数为None(None通常是一个很好的选择),每次调用时创建一个新对象。
def append_to(element, to=None):
if to is None:
to = []
to.append(element)
return to
同时也有注意,该函数要传递一个list对象作为第二个参数,因为函数中对它进行了append操作。
文章首发于我的技术博客猿人学Python基础教程
在python中,用默认参数(list,set,dict...)时要小心的更多相关文章
- Python中的默认参数(转)
add by zhj: Python设计者为何将默认参数设计成这样呢?参见Python函数参数默认值的陷阱和原理深究 原文:https://github.com/acmerfight/insight_ ...
- python中的默认参数
https://eastlakeside.gitbooks.io/interpy-zh/content/Mutation/ 看下面的代码 def add_to(num, target=[]): tar ...
- python 中函数的参数
一.python中的函数参数形式 python中函数一般有四种表现形式: 1.def function(arg1, arg2, arg3...) 这种是python中最常见的一中函数参数定义形式,函数 ...
- Python中函数的参数-arguments
归纳起来,Python中函数的定义形式和调用形式主要有如下几种形式: # 函数的定义形式 def func(name) # 匹配positional参数或者keyword参数 def func(nam ...
- Python进阶-函数默认参数
Python进阶-函数默认参数 写在前面 如非特别说明,下文均基于Python3 一.默认参数 python为了简化函数的调用,提供了默认参数机制: def pow(x, n = 2): r = 1 ...
- C++中的默认参数规则
C++中的默认参数规则 C++的默认参数规则其实是一个非常容易掉坑的规则,尤其是当一个函数拥有多个声明的时候,每个声明的默认参数可以各不相同,在调用时又可能与每个声明都不同:这篇博客稍微列举一下C++ ...
- Python中函数传递参数有四种形式
Python中函数传递参数有四种形式 fun1(a,b,c) fun2(a=1,b=2,c=3) fun3(*args) fun4(**kargs) 四种中最常见是前两种,基本上一般点的教程都会涉及, ...
- 讲讲python中函数的参数
python中函数的参数 形参:定义函数时代表函数的形式参数 实参:调用函数时传入的实际参数 列如: def f(x,y): # x,y形参 print(x, y) f(1, 2) # 1, 2 实参 ...
- python中的魔法参数:*args和**kwargs
python中的魔法参数:*args和**kwargs def foo(*args, **kwargs):print 'args = ', argsprint 'kwargs = ', kwargsp ...
随机推荐
- CentOS8 安装 simple-scan 的方法
CentOS8删除了很多软件包,解决的思路一般是从CentOS7或EPEL7的软件仓库中寻找,并解决依赖关系. 比如找到EPEL7中有 simple-scan 软件包,但安装时发现其又依赖 gnome ...
- Ansible-galera
在四台虚拟机上都安装好docker 一.控制节点 1. 域名解析 [root@d ansible]# vim /etc/hosts [root@d ansible]# scp /etc/hosts n ...
- Day03:文本数据IO操作 / 异常处理
文本数据IO操作 Reader和Writer 字符流原理 Reader是字符输入流的父类 Writer是字符输出流的父类. 字符流是以字符(char)为单位读写数据的.一次处理一个unicode. ...
- JS自适应导航栏,菜单栏
1. 打开 https://github.com/VPenkov/okayNav下载源代码 2.引入两个css样式 <link rel="stylesheet" href=& ...
- Ubuntu16.04下使用pycharm导入scrapy框架
出现迷之问题,ubuntu终端下安装的库在pycharm中无法识别 后重新为pycharm安装相关package,得以使用 看到3即可 https://www.cnblogs.com/airnew/p ...
- (模板)luoguP3806(树上点分治模板题)
点分治的写法1: 题目链接:https://www.luogu.org/problem/P3806 题意:给出一颗带边权的树,结点数n<=1e4,每条边有权值<=1e4,有m组询问(m&l ...
- Java判断指定日期是否为工作日
Java判断指定日期是否为工作日 转自:https://www.jianshu.com/p/966659492f2f 转:https://www.jianshu.com/p/05ccb5783f65转 ...
- 大数据之Zookeeper概述
Zookeeper概述 Zookeeper是一个开放源码的分布式应用程序协调服务,是 Google的Chubby一个开源的实现,是 Hadoop和 HBASE的重要组件.主要解决分布式应用一致性问题. ...
- 使用foreach的禁忌
List<String> list = new ArrayList<>(); Iterator<String> iterator = list.iterator() ...
- CString VariantToString(VARIANT var);转换
Variant类型转换成CString代码 对数据库的操作常常会用Variant和_bstr_t类型,在进行MFC等程序中,通常会用到CString类.从variant转换成CString代码如下:v ...