Python如何访问构造函数参数作为类其他方法的默认参数
报错原因
这个错误的核心是Python函数默认参数的求值时机和常规认知有差异:
- 不管是普通函数还是类的方法,默认参数都是在函数/方法定义的那一刻就完成求值、固定绑定的,不是每次调用的时候再动态计算。你写
edit_profile方法定义的时候,Python正在解析类的代码,此时还没有创建过任何Customer的实例,而self本身就是实例调用方法时才会自动传入的实例引用,定义阶段根本不存在self这个变量,当然访问不到self.name。 - 而方法内部的代码,是你实际调用
实例.edit_profile()的时候才会执行,这时候实例已经存在,self已经被自动传到方法的作用域里,自然可以正常读写self.name这类实例属性。
这也是Python里经典的“不要用可变对象当默认参数”的底层原因,比如你写
def func(a=[]),这个空列表是定义函数的时候就生成的,之后所有调用这个函数不传a的时候,用的都是同一个列表对象,很容易出现数据互相污染的bug。
正确实现方法
用None当占位的默认哨兵值,在方法内部做判断,如果调用的时候没传new_name,就把当前实例的self.name当默认值用即可:
class Customer: def __init__(self , name, gender, address): self.name = name self.gender = gender self.address = address def edit_profile(self, new_city, new_gender, new_address, new_name=None): # 没传new_name的话,默认保持当前name不变 if new_name is not None: self.name = new_name self.gender = new_gender self.address = new_address # 注:原代码里的new_city参数未做对应赋值,如果需要单独维护城市属性,可在__init__中新增对应实例属性后在此处赋值更新
调用效果参考:
if __name__ == "__main__": cust = Customer("张三", "男", "北京市朝阳区") # 不传new_name,name保持为张三 cust.edit_profile("上海市", "男", "上海市浦东新区") print(cust.name) # 输出:张三 # 传new_name则更新name cust.edit_profile("广州市", "男", "广州市天河区", new_name="张三丰") print(cust.name) # 输出:张三丰
内容的提问来源于stack exchange,提问作者Abhinab k
相关产品推荐
相关产品推荐

