我正在尝试在我已编写的函数中使用函数,它可以与list comprehension
和部分函数一起使用,但不能与lambda
函数一起使用。
所以我的功能是:
import numpy as np
from scipy.optimize import minimize
from _functools import partial
from sklearn.metrics import mean_squared_error
arpdau = np.random.randint(0,100,15)
def fitARPDAU(arpdau, max_cohortday, method, par=None):
valid = {'log', 'power', 'all'}
if method not in valid:
raise ValueError("results: method must be one of %r." % valid)
values = par
if method == 'log':
if values == None:
a = 1
b = 0
c = 1
values = [a, b, c]
bounds = [(1e-10, None), (1e-10, None), (None, None)]
def getArpdauFunction(x, values):
return values[0] * np.log(x + values[1]) + values[2]
elif method == 'power':
if values == None:
a = 1
b = 0
c = .5
d = 0
values = [a, b, c, d]
bounds = [(1e-10, None), (None, None), (1e-10, 1), (None, None)]
def getArpdauFunction(x, values):
return values[0] * (x + values[1]) ** values[2]+ values[3]
elif method == 'all':
log_loss = fitARPDAU(arpdau, max_cohortday, method='log', par=par)
power_loss = fitARPDAU(arpdau, max_cohortday, method='power', par=par)
combined_models = [log_loss, power_loss]
losses = map(lambda x: x[0].fun, combined_models)
return combined_models[np.argmin(losses)]
def getLossOptim(values):
# import ipdb; ipdb.set_trace()
# arpdau_pred = [getArpdauFunction(x, values) for x in range(max_cohortday)]
arpdau_pred_1 = map(lambda x: getArpdauFunction(x, values), range(max_cohortday))
# arpdau_pred_2 = partial(getArpdauFunction, values=values)(range(271))
return mean_squared_error(arpdau, arpdau_pred_1[:len(arpdau)])
result = minimize(getLossOptim, values, method='L-BFGS-B', bounds=bounds)
return result, [getArpdauFunction(x, result.x) for x in range(max_cohortday)], result.x, method, getArpdauFunction
print fitARPDAU(arpdau, 100, method='all', par=None)
getLossOptim中是否存在部分和列表理解有效的原因,但lambda函数不起作用?
lambda
函数返回
NameError: global name 'getArpdauFunction' is not defined
谢谢!
这与在另一个函数内定义的函数无关。如果method
不是'log'
或'power'
,那么getArpdauFunction()
永远不会定义。
您可能应该为所有内容定义它,然后如果方法是'log'
或'power'
则重载它。
这与您的问题没有关系,但您也不应该使用if x == None
。因为None
是单身,所以使用if x is None
更有效率和pythonic
正如我在评论中所说,你的问题与在另一个函数中定义的函数无关。您收到错误的原因是因为函数有时未定义;如果method
既不是'log'
也不是'power'
,那么getArpdauFunction()
永远不会定义。
这很容易解决。我现在能看到的最干净的方法是声明几个函数,然后动态选择一个:
def identity(x): return x
def pp(x): return x+1
def mm(x): return x-1
functions = {
"++": pp,
"--": mm
}
default_function = identity
print(functions.get("++", default_function)(2)) # 3
print(functions.get("--", default_function)(2)) # 1
print(functions.get("non existing function name", default_function)(2)) # 2
如果你的功能非常短(如本例所示,那么你可以直接写:
functions = {
"++": lambda x: x+1,
"--": lambda x: x-1
}