由于这是一个简短的问题,我会遗漏常规背景信息(如果您需要,我会添加它)。 最后有一个名为Coefficients的数据框
Serial_number Fixed_effects_beta_0 Fixed_effects_beta_1 Fixed_effects_beta_2 Fixed_effects_beta_3 Random_effects_beta_0 Random_effects_beta_1 Random_effects_beta_2 Random_effects_beta_3 p0_fixed p1_fixed p2_fixed p3_fixed p0_random p1_random p2_random p3_random Fitted_Voltage
1 912009913 1.238401 13.19572 -0.08379988 1.366747 -0.039642999 -0.40767221 -0.25476169 -0.11315457 -11.92334 0.1177605 -0.0003777831 4.328852e-07 0.56414753 -0.006946270 2.736287e-05 -3.583906e-08 352.9476
(...)
并且对于每行我想要应用函数
inverse = function (f, lower = lower_limit, upper = 450) {
function (y) uniroot((function (x) f(x) - y), lower = lower_limit, upper = upper)[1]
# function (y) polyroot((function (x) f(x) - y), lower = lower_limit, upper = upper)[1]
}
function_to_observe = inverse((function(x=150)
exp(
exp(
sum(
Coefficients[running_row,"p0_fixed"] * x^0,
Coefficients[running_row,"p1_fixed"] * x^1,
Coefficients[running_row,"p2_fixed"] * x^2,
Coefficients[running_row,"p3_fixed"] * x^3
))
)
)
, 50, 450)
通过使用存储在数据帧的每一行和某些列中的值,如下所示:
for(i in 1:nrow(Coefficients)){
Coefficients[i,"Fitted_Voltage"]<- function_to_observe(150)
}
不幸的是,这不起作用,因为Coefficients[i,"Fitted_Voltage"]<- function_to_observe(150)
没有处理不同的系数行。
什么是补救措施?为什么我不能做到以下几点:
for(i in 1:nrow(Coefficients)){
Coefficients[i,"Fitted_Voltage"]<- inverse((function(x=150)
exp(
exp(
sum(
Coefficients[i,"p0_fixed"] * x^0,
Coefficients[i,"p1_fixed"] * x^1,
Coefficients[i,"p2_fixed"] * x^2,
Coefficients[i,"p3_fixed"] * x^3
))
)
)
, 50, 450)
}
这会产生:
Error in x[[jj]][iseq] <- vjj :
incompatible types (from closure to double) in subassignment type fix
非常感谢您提供任何帮助!
# Update:
With the help of mathdotrandom I tried a bit and get the following:
lower_limit<- 0
function_to_observe<- inverse((function(x=150)
exp(
exp(
sum(
Coefficients[i,"p0_fixed"] * x^0,
Coefficients[i,"p1_fixed"] * x^1,
Coefficients[i,"p2_fixed"] * x^2,
Coefficients[i,"p3_fixed"] * x^3
))))
, 50, 550
)
inverse = function (f, lower = lower_limit, upper = 450) {
function (y) uniroot((function (x) f(x) - y), lower = lower_limit, upper = upper)[1]
}
for(i in 1:nrow(Coefficients)){
Coefficients[i, "Fitted_Voltage"]<- function_to_observe(150)
}
Coefficients["Fitted_Voltage"]
产生合理的值:
Fitted_Voltage
1 352.9476
2 352.9476
3 352.9476
4 352.9476
5 352.9476
6 352.9476
7 352.9476
8 352.9476
9 352.9476
10 352.9476
11 352.9476
12 352.9476
13 352.9476
14 352.9476
15 352.9476
虽然我不理解语法,但我认为这是正确的,因为它做了应有的事情。
答案 0 :(得分:1)
function(x = 150)不运行该函数,但将x设置为默认参数150.因此,您尝试将函数定义放入data.frame中。这就是为什么它抱怨类型闭包(函数)。最简单的方法是给函数命名并在for循环之外定义它,然后调用它。
如果你真的想用它作为lambda函数结帐这个问题和lebatsnok回答:lambda-like functions in R?
反函数不应返回函数而是返回数字。 uniroot函数需要一个函数,所以f应该是你所做的函数。如果你不把它作为参数,R实际上会从上面查找i或running_row的值。
Coefficients <- data.frame("Fitted_Voltage"=c(0,0), "p0_fixed"=c(10^-1, 10^-2),
"p1_fixed"=c(10^-2, 10^-3), "p2_fixed"=c(10^-3, 10^-4),
"p3_fixed"=c(10^-4, 10^-5))
f <- function(x=150)exp(exp(sum(Coefficients[running_row,"p0_fixed"] * x^0,
Coefficients[running_row,"p1_fixed"] * x^1,
Coefficients[running_row,"p2_fixed"] * x^2,
Coefficients[running_row,"p3_fixed"] * x^3)))
inverse = function (f, lower_limit, upper = 450) {
y = (f(lower_limit) + f(upper))/2
uniroot(function(x)(f(x)-y), lower = lower_limit, upper = upper)[1]
}
for(running_row in 1:nrow(Coefficients)){
Coefficients[i, "Fitted_Voltage"] <- inverse(f,-1,1)
}
但是你的函数总是正数,因为你使用exp和exp(x)&gt; 0 forall x,所以uniroot找不到该函数的零。多根也只能找到多项式的零,但你使用的是exponentail函数。你确定你的函数应该是这样的:e ^(e ^(c_0 + c_1 * x + c_2 * x ^ 2 + c_3 * x ^ 3))? 我减去一个倒数的值,使它有一个根,但我不知道这是否在你的上下文中有任何意义。同样由于双指数,函数变得非常快,所以即使对于小系数,它也会返回Infinity的下限50和上限450,所以我需要做-1和1作为限制来获得一些结果。但这应该与你想要的方式类似。
答案 1 :(得分:1)
遵循mathdotrandom的建议。您可以在外面定义功能。试试这个:
inner.f <- function(x=150, i){
exp(
exp(
sum(
Coefficients[i,"p0_fixed"] * x^0,
Coefficients[i,"p1_fixed"] * x^1,
Coefficients[i,"p2_fixed"] * x^2,
Coefficients[i,"p3_fixed"] * x^3
))
)
}
然后(如果你想将x设置为150)
Coefficients[i,"Fitted_Voltage"]<- inverse(inner.f(150, i), 50, 450)