Search code examples
rloopsgradient

R loop until condition is met


Working on a project in R, I got stuck somewhere. Those are my data:


r <- 0.001
a <- 0.386
b <- 0.799

yp <- b*df$x+a
sse <- ((df$y-yp)^2)*0.5
a <- a-r*sum(-(df$y-yp))
b <- b-r*sum(-(df$y-yp)*df$x)

How can I find the number of iterations until SSE error is 0.0001?


Solution

  • You could do a while loop that stores the sum of squared errors in a vector for each iteration. The loop stops when the sum of squares stops falling, at which point we should have an accurate a and b, and the number of iterations is given by the length of the sse vector.

    df <- data.frame(x=c(1.0,2.1,2.2,3.5,5.3,5.4,6.5,7.4),
                     y=c(4,4,4,5,5,6,8,8))
    
    r <- 0.001
    a <- 0.386
    b <- 0.799
    
    yp  <- b * df$x + a
    sse <- sum(((df$y - yp)^2))
    
    while(TRUE)
    {
      a <- a - r * sum(-(df$y - yp))
      b <- b - r * sum(-(df$y - yp) * df$x)
      yp <- b * df$x + a
      sse <- c(sse, sum((df$y - yp)^2))
      if(tail(sse, 1) >= sse[length(sse) - 1]) break
    }
    

    To see the results, we can do:

    cat('iterations: ', length(sse), '\n Intercept = ', a, '\n Slope = ', b, '\n')
    #> iterations:  9152 
    #>  Intercept =  2.691678 
    #>  Slope =  0.6726519
    

    And we can see that our results are correct (to the first six decimal places) by running an lm:

    coef(lm(y~x, df))
    #> (Intercept)           x 
    #>   2.6916789   0.6726517
    

    Created on 2022-03-15 by the reprex package (v2.0.1)