在R中,我想采用一种方法来获取公式右侧的符号导数,其中可能包括交互项,平方项等。
例如,我希望能够对x中的以下两个[edit:three]公式中的每一个的右侧进行导数:
Y〜X + I(X ^ 2)
Y〜X位:Z
编辑:y~x * z
我想要一个函数,当输入上述三个公式中的每一个时,它们分别返回1 + 2x,z和1 + z。
我尝试了以下内容:
f1<-y~x+I(x^2)
deriv(f1,"x")
## Error in deriv.formula(f1, "x") : Function 'I' is not in the derivatives table
f2<-y~x:z
deriv(f2,"x")
## Error in deriv.formula(f2, "x") : Function '`:`' is not in the derivatives table
有没有办法迫使R将I(x ^ 2)(或类似地,I(x * z)等)识别为x ^ 2(分别为x * z),x:z为x为了计算导数,* z(在数学意义上)和x * z(在公式意义上)为x + z + x * z(在数学意义上)?
第二,有没有办法从deri()获取输出并将其重塑为公式的右侧?特别是,我知道D()将缓解这个问题并以我想要的形式生成输出(虽然D()不能处理公式作为输入),但是如果我想对多个变量采取衍生物怎么办?我可以通过反复对每个变量应用D()来解决这个问题,但我只想输入所有这些变量的字符串并接收适合放置的输出,这样会很好。在公式的右侧。
谢谢!
答案 0 :(得分:2)
如果您有公式表达式,可以使用substitute():
使用它substitute( x~x:z+x:y , list(`:`=as.name("*") ) )
x ~ x * z + x * y
这将允许您将表达式对象传递给substitute
,并首先对其进行评估(否则,由于substitute
未评估其第一个参数,因此不会发生这种情况):
form1 <- expression(x ~ x : z + x : y)
rm(form2)
form2 <- do.call('substitute' , list(form , list(`:`=as.name("*") ) ))
form2
# expression(x ~ x * z + x * y)
这显示了如何“重塑”RHS以便y ~ x:z
像~ x*z
一样处理,方法是从列表结构中提取RHS,其中波形符操作符被视为一个函数,而LHS是(~ , <LHS>, <RHS>)
中的第二个元素:
f2<-y~x:z
substar <- function(form) {
do.call('substitute' , list(form , list(`:`=as.name("*") ) )) }
f3 <- substar(f2)
deriv(f3[[3]],"x")
#----------------------
expression({
.value <- x * z
.grad <- array(0, c(length(.value), 1L), list(NULL, c("x")))
.grad[, "x"] <- z
attr(.value, "gradient") <- .grad
.value
})
如果你想使用表达式,可能有助于理解它们像列表一样被组织,并且运算符实际上是类似Lisp的函数:
> Z <- y~x+I(x^2)
> Z
y ~ x + I(x^2)
> Z[[1]]
`~`
> Z[[2]]
y
> Z[[3]]
x + I(x^2)
> Z[[3]][[1]]
`+`
> Z[[3]][[2]]
x
> Z[[3]][[3]]
I(x^2)
> Z[[3]][[3]][[1]]
I
> Z[[3]][[3]][[2]]
x^2
> Z[[3]][[3]][[2]][[1]]
`^`
如果你想看一个将遍历表达式树的函数,几年前无与伦比的Gabor Grothendieck在Rhelp构建了一个函数:http://markmail.org/message/25lapzv54jc4wfwd?q=list:org%2Er-project%2Er-help+eval+substitute+expression
答案 1 :(得分:1)
deriv
(?deriv
)的帮助文件表示expr
函数中的deriv
参数为“
表达式或调用或(除了D)没有lhs的公式“。所以你不能在表达式中使用等式的左边。
在问题的第二部分,如果我正确地理解了你的问题,你可以做这样的事情:说你的rhs是x ^ 2 + y ^ 2你需要用x和y取这个表达式的偏导数:
myexp <- expression((x^2) + (y^2))
D.sc.x <- D(myexp, "x")
> D.sc.x
2 * x
D.sc.y <- D(myexp, "y")
> D.sc.y
2 * y
在一行中:
lapply(as.list(c("x","y")),function(a)D(myexp,a))
[[1]]
2 * x
[[2]]
2 * y