LeetCode提交climbStairs解法报NameError及类、self关键字作用疑问
问题解答
类内递归调用报错的原因
你遇到的NameError: global name 'climbStairs' is not defined报错确实和作用域有关:
- 类中定义的实例方法不属于全局作用域,直接写
climbStairs()只会在全局作用域查找同名函数,自然找不到属于Solution类的方法。 - 类实例方法内部调用自身类的其他方法,必须通过实例本身引用,也就是用类方法约定的第一个参数
self调用,修复后的代码如下:
class Solution(object): def climbStairs(self, n): if n in {0,1}: return 1 else: return self.climbStairs(n-2) + self.climbStairs(n-1)
不同版本代码运行差异的原因
- 带
self的独立函数报错原因self只有在类的实例方法中才有特殊含义,作为独立函数定义时,它只是一个普通的位置参数名。你定义时声明了两个参数self和n,但递归调用时只传了1个参数,自然会报参数缺失的错误。 - 去掉
self的独立函数正常运行的原因
此时函数只有1个参数n,递归调用时传参数量匹配,且函数在全局作用域定义,递归调用时可以正常找到同名函数,所以运行正常。
类定义、self关键字、继承object的作用与适用场景
类(class)
- 作用:面向对象编程的核心单元,用来封装关联的属性(数据)和方法(功能),支持模块化复用、继承、多态等面向对象特性。LeetCode要求把解法写在固定的
Solution类中,是为了统一平台的调用逻辑,方便批量执行测试用例。 - 适用场景:需要封装多组关联功能、需要创建多个状态独立的实例、需要使用继承/多态等特性时使用,单个独立的工具函数不需要用到类。
self关键字
- 作用:Python类实例方法的第一个参数的约定名称,当你通过实例调用方法时,Python会自动把当前实例对象作为第一个参数传入
self,用于在方法内部访问当前实例的其他属性和方法。 - 适用场景:所有类的实例方法都需要把
self作为第一个参数,类方法(@classmethod)第一个参数约定为cls,静态方法(@staticmethod)不需要传入实例引用,所以不需要self。
继承object
- 作用:这是Python2的遗留写法,Python2中显式继承
object的类是新式类,不继承的是旧式类,两者在方法查找顺序、内置特性支持上有差异。Python3中所有类默认继承object,属于新式类,写不写继承object效果完全一致。 - 适用场景:只有需要兼容Python2运行的代码才需要显式声明继承
object,否则不需要额外添加。
内容的提问来源于stack exchange,提问作者KrazyKoder67
相关产品推荐
相关产品推荐

