1

There is a function like: y = (e^x - 2)^n

The x is an unknown, for n = 2,3,4,...,8 Now I want to use NR method to find the root of this function(initial x is 0).

I know how to write an NR method if the n is a fixed value, here's my origin NR code:

NR <- function(f, x0, tol = 1e-5, ite = 1000){
require(numDeriv)   #call the package for computing dx
k <- ite

for (i in 1:ite){
    #calculate dx
    dx <- genD(func = f, x = x0)$D[1]

    #get the x1
    x1 <- x0 - (f(x0) / dx)
    k[i] <- x1
    if(abs(x1 - x0) < tol){
        root <- x1
        re <- list('root approximation' = root, 'iteration' = length(k))
        return(re)
    }
    x0 <- x1
}
print('Outside the upper iteration')
}

Now I rewrite my function:

f <- function(x, n){
(exp(x) - 2) ^ n
}

If I want to output every root for different n, I think I should add another loop before the loop "for (i in 1:ite)" So I rewrite my NR function code:

NR <- function(f, x0, tol = 1e-5, ite = 1000){
require(numDeriv)   #call the package for computing dx
k <- ite
for(n in 2:8){
    for (i in 1:ite){
        #calculate dx
        dx <- genD(func = f, x = x0)$D[1]

        #get the x1
        x1 <- x0 - (f(x0, n) / dx)
        k[i] <- x1
        if(abs(x1 - x0) < tol){
            root <- x1
            re <- list('root approximation' = root, 'iteration' = length(k))
            return(re)
        }
        x0 <- x1
    }
    print('Outside the upper iteration')
}
} 

But when I run NR(f,0), R showed me the error is : Error in func(x, ...) : argument "n" is missing, with no default

How can I figure this out? Thank you for your help!

Hongbing
  • 11
  • 1
  • 1
    Side note: you should almost always use `library`, not `require`. The latter never stops following code when the package is not available, which is almost never what is intended. If you want to use `require`, then save its return value and do something with it (e.g., fail gracefully, use other functions, etc). Refs: https://stackoverflow.com/a/51263513/3358272 – r2evans Jan 26 '19 at 22:23

1 Answers1

0

I hope you find my answer helpful: If you try ?genD you will read this:

Usage

genD(func, x, method="Richardson",
               method.args=list(), ...)
## Default S3 method: genD(func, x, method="Richardson",
  method.args=list(), ...) Arguments

func a function for which the first (vector) argument is used as a parameter vector. x The parameter vector first argument to func.

And in the bottom of the R Documentation this example:

Examples

func <- function(x){c(x[1], x[1], x[2]^2)}
z <- genD(func, c(2,2,5))

Therefore, the issue with your code is that you need to use a vector as an argument for f:

f <- function(c){   (exp(c[1]) - 2) ^ c[2] }

NR <- function(f, x0, tol = 1e-5, ite = 1000){   require(numDeriv)  
#call the package for computing dx   k <- ite   for(n in 2:8){
    for (i in 1:ite){
      #calculate dx
      dx <- genD(func = f, x = c(x0,n))$D[1]

      #get the x1
      x1 <- x0 - (f(c(x0,n)) / dx)
      k[i] <- x1
      if(abs(x1 - x0) < tol){
        root <- x1
        re <- list('root approximation' = root, 'iteration' = length(k))
        return(re)
      }
      x0 <- x1
    }
    print('Outside the upper iteration')   } } 

NR(f,0)

If I run that my output is:

$`root approximation` [1] 0.6931375

$iteration [1] 15

Best!

LocoGris
  • 4,432
  • 3
  • 15
  • 30