问题描述
class A:
def _add(a,b):
return a + b
def f_add():
return _add
def lambda_add():
return lambda x,y: _add(x,y)
def lambda_arg_add(l=lambda x,y)):
return l
def partial_add():
return partial(_add)
def partail_arg_add(f=partial(_add)):
return f
A.f_add()(1,2)
A.lambda_add()(1,2)
A.lambda_arg_add()(1,2)
A.partial_add()(1,2)
A.partail_arg_add()(1,2)
除最后一个之外的所有函数调用都会引发错误,指出 _add
未定义,但对 partail_arg_add
的调用成功执行。这背后的逻辑是什么?为什么解释器在创建偏函数时知道在哪里查找 _add
而只有在它作为默认参数完成时才知道?
解决方法
functools.partial 不参与此行为。
这是因为默认 arg 是在函数定义中创建的,在类定义期间,发生在类的范围内,因此您不需要任何“自我”。
这就是为什么这样做:
class Example:
def A(self):
pass
def B(self,x=print(A,1)):
print(self.A,2)
print(A,3)
输出:
<function Example.A at 0x7fcf8ebc5950> 1
<function Example.A at 0x7fcf8ebc5950> 3
即使没有调用任何 Example.B()
,它也应该在定义类时打印 <function Example.A at 0x7fcf8ebc5950>
1 和 3。
但是您不能使用尚未创建的类的方法创建部分
或者,也许你可以,但我不知道有什么方法可以做到。
我试图修复你的课程:
class A:
@staticmethod
def _add(a,b):
return a + b
@classmethod
def f_add(cls): # valid
return cls._add
@classmethod
def lambda_add(cls): # valid
return lambda x,y: cls._add(x,y)
@staticmethod
def lambda_arg_add(l=lambda x,y: A._add(x,y)): # valid
return l
@classmethod
def partial_add(cls): # valid
return partial(cls._add)
@staticmethod
def partial_arg_add(f=partial(_add)): # TypeError: 'staticmethod' object is not callable
return f
但是partial_arg_add 会失败,因为在创建partial 时_add 还不能调用:
class A:
@staticmethod
def _add(a,b):
return a + b
print(_add(1,3)) # TypeError: 'staticmethod' object is not callable
class A:
@staticmethod
def _add(a,b):
return a + b
print(A._add(1,3)) # 4