R中的三重积分(如何指定域)

时间:2015-04-04 15:28:23

标签: r integral

我想在R中计算三个变量f(x,y,z)的函数的三重积分。我正在使用包cubature和函数adaptIntegrate()。被积函数仅在某个域(x<y<z,等于0)中等于1,我不知道如何指定。我正在尝试两种不同的函数实现,但它们都不起作用:

#First implementation
fxyz <- function(w) {
x <- w[1]
y <- w[2]
z <- w[3]
x*y*z*(x < y)&(y < z)
}

#Second implementation
fxyz <- function(w) {
x <- w[1]
y <- w[2]
z <- w[3]
if(x<y&y<z)
    out<-1
else
    out<-0
out
}

#Computation of integral
library(cubature)
lower <- rep(0,3)
upper <- rep(1, 3)
adaptIntegrate(f=fxyz, lowerLimit=lower, upperLimit=upper, fDim = 3)

有关如何正确指定域的任何想法吗?

3 个答案:

答案 0 :(得分:1)

我不了解cubature软件包,但您可以通过重复应用基础R integrate函数进行一维集成来实现此目的。

f.xyz <- function(x, y, z) ifelse(x < y & y < z, 1, 0)
f.yz <- Vectorize(function(y, z) integrate(f.xyz, 0, 1, y=y, z=z)$value,
                  vectorize.args="y")
f.z <- Vectorize(function(z) integrate(f.yz, 0, 1, z=z)$value,
                 vectorize.args="z")

integrate(f.z, 0, 1)
# 0.1666632 with absolute error < 9.7e-05

您可能希望使用控制参数来设置数字容差;内部整合中的小错误可以在外部变成大错误。

答案 1 :(得分:1)

在您的第一个函数中,返回值是错误的。它应该是as.numeric(x<=y)*as.numeric(y<=z)。在第二个函数中,您还应该使用<=而不是<,否则`adapIntegrate将无法正常工作。您还需要指定最大评估数。试试这个

library(cubature)
lower <- rep(0,3)
upper <- rep(1,3)

# First implementation (modified)
fxyz <- function(w) {
    x <- w[1]
    y <- w[2]
    z <- w[3]
    as.numeric(x <= y)*as.numeric(y <= z)
}

adaptIntegrate(f=fxyz,lowerLimit=lower,upperLimit=upper,doChecking=TRUE,
          maxEval=2000000,absError=10e-5,tol=1e-5)
#$integral
#[1] 0.1664146
#$error
#[1] 0.0001851699
#$functionEvaluations
#[1] 2000031
#$returnCode
#[1] 0

答案 2 :(得分:0)

0 <= x <= y <= z <= 1是“规范”单纯形。要通过单纯形进行集成,请使用SimplicialCubature包。

library(SimplicialCubature)
f <- function(x) 1
S <- CanonicalSimplex(3)

> adaptIntegrateSimplex(function(x) 1, S)
$integral
[1] 0.1666667

$estAbsError
[1] 1.666667e-13

$functionEvaluations
[1] 55

$returnCode
[1] 0

$message
[1] "OK"

请注意,将常数函数f(x)=1集成到单纯形上只会得到单纯形的体积,即1/6。集成对于此示例没有用。

> SimplexVolume(S)
[1] 0.1666667