【问题标题】:Function produces NA when increasing size of data增加数据大小时函数产生 NA
【发布时间】:2019-03-15 03:59:15
【问题描述】:

我正在 R 中实现我的函数并尝试根据结果来确定它是否符合我的预期。我要评估的功能是:

在我增加数据矩阵的大小之前,该函数可以正常工作(例如,它适用于 N = 10,但不适用于 N = 12,下面将发布示例。)

我确定是否与我的实现或溢出问题有关。

# Generate Sample Data
gen.sample <- function(n){
  x <- runif(n,min = -5,max = 5)
  y <- ifelse(x < 0,-1,1)
  return(data.frame(x,y))
}

# Objective function L_D
obj_fun <- function(X,y,alpha){
  N <- length(X) 
  inner.product <- numeric(N)
  for(i in 1:N){
    for(k in 1:N){
      inner.product[k] <- alpha[i]*alpha[k]*
        y[i]*y[k]*(t(as.numeric(X[i]))%*%as.numeric(X[k]))
    }
  }
  L_D <- sum(alpha) - 0.5*sum(inner.product)
  return(L_D)
}

# L_D works when N = 10
set.seed(4997)
options(digits = 4,scipen = -4)
N = 10
sample.data <- gen.sample(n=N)
X.data <- sample.data$x
y.vec <- sample.data$y

alpha.vector <- matrix(rep(c(-5,-4,-3,-2,-1,0,1,2,3,4,5),11*N),ncol = 11, nrow = N, byrow = TRUE)
for(j in 1:N){
  alpha.vector[j,2] <- rnorm(1,5,5)
}

for(i in 1:N){
  print(obj_fun(X = X.data, y = y.vec, alpha =  alpha.vector[i,]))
}

# It produces all NA when N = 12

set.seed(4997)
options(digits = 4,scipen = -4)
N = 12
sample.data <- gen.sample(n=N)
X.data <- sample.data$x
y.vec <- sample.data$y

alpha.vector <- matrix(rep(c(-5,-4,-3,-2,-1,0,1,2,3,4,5),11*N),ncol = 11, nrow = N, byrow = TRUE)
for(j in 1:N){
  alpha.vector[j,2] <- rnorm(1,5,5)
}

for(i in 1:N){
  print(obj_fun(X = X.data, y = y.vec, alpha =  alpha.vector[i,]))
}
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA
[1] NA

出了什么问题?我没有看到问题。

任何帮助都会很棒!

【问题讨论】:

  • 在你刚刚添加的tex格式的数学方程中,alpha、y和x的维度是多少?它们都是长度为 n 的向量吗?还是 x 是一个 n*n 矩阵?还是别的什么?
  • @DanY 你好 Dan,alpha 的维度应该是一个 1×N 的向量,y 应该是一个 1×N 的向量,x 是数据(对于这个简单的例子),1×N . 稍后当我让我的代码适用于 1D 数据时,我将对其进行更多修改以适用于 2D 案例。我现在要做的就是评估我的函数 L_D 并绘制它以查看它是否是二次的。
  • 我刚刚修改了下面的答案,将newfun() 包括在内,我认为这是您上面提供的数学方程式的忠实实现。
  • @DanY 我在上面修复了我的代码,它可以工作。我仍在研究为什么我的情节看起来不像二次函数。我所做的只是:L_D_eval

标签: r for-loop optimization


【解决方案1】:

问题出在obj_fun 中的这个循环中,涉及到您在alpha 中使用的内容:

for(i in 1:N){
    for(k in 1:N){
      inner.product[k] <- alpha[i]*alpha[k]*...
    }
  }

两件事:

(1) 你设置了N=12,但你调用obj_fun(..., alpha=alpha.vector[i,]),其中alpha.vector[i,] 是长度为11 的向量。我在上面粘贴的循环尝试访问alpha[i],而i=NNA因为alpha中没有第12个元素

(2) 注意当你单步执行你的双循环时会发生什么:当i=1k=1 时,你给inner.product[1] 赋值。然后i=1k=2inner.product[2] 赋值。这很好,直到i 更改为i=2。当i=2k=1 时,您通过为其分配一个新值来覆盖inner.product[1]。这一直持续到i=Nk=N,此时您将覆盖所有kinner.product[k],但这次使用NA,因为您执行涉及alpha[i]alpha[k] 的计算,正如刚才解释的那样在上面的(1)中,都是alpha 的“外部”。因此,所有inner.product 都充满了NA


编辑:根据您添加到问题中的数学方程式,以及您指出 alphaxy 都是长度为 n 的向量,我相信这个函数会满足您的要求:

newfun <- function(x, y, alpha) {
    axy <- alpha*x*y
    sum(alpha) - 0.5*sum(outer(axy, axy, "*"))
}

【讨论】:

  • 嗨,丹,非常感谢您的评论。这是有价值的。我在想一种方法来评估双重和。
  • 嗨,丹,所以如果我想绘制我的函数“newfun”,我如何使用想法图(L_D~alpha.vec)来绘制它?我表示 L_D
  • L_D &lt;- newfun(...); plot(x=alpha.vec, y=L_D)
  • 也许ay &lt;- alpha*y; sum(alpha) - 0.5*sum(outer(ay, ay, "*")*crossprod(x))
【解决方案2】:

试试这个:

set.seed(4997)
options(digits = 4,scipen = -4)
N = 12
sample.data <- gen.sample(n=N)
X.data <- sample.data$x
y.vec <- sample.data$y

    alpha.vector <- matrix(rep(c(-6,-5,-4,-3,-2,-1,0,1,2,3,4,5,6),13*N),ncol = 13, nrow = N, byrow = TRUE)
    for(j in 1:N){
      alpha.vector[j,2] <- rnorm(1,5,5)
    }

for(i in 1:N){
  print(obj_fun(X = X.data, y = y.vec, alpha =  alpha.vector[i,]))
}

问题就在这里:

obj_fun <- function(X,y,alpha){

  N <- length(X) 
  inner.product <- numeric(N)
  for(i in 1:N){
    for(k in 1:N){
      inner.product[k] <- alpha[i]*alpha[k]*
        y[i]*y[k]*(t(as.numeric(X[i]))%*%as.numeric(X[k]))
    }
  }
  L_D <- sum(alpha) - 0.5*sum(inner.product)
  return(L_D)
}

此函数从 1 循环到 12,但 alpha 没有元素 1211

顺便说一句:可以通过使用apply family 和其他更改来改进这种循环执行代码的方式!

【讨论】:

  • 您好,我不知道如何在这里使用“应用”,但我会试一试。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-05-22
  • 1970-01-01
  • 2013-09-10
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多