如何使用fsolve函数在R中找到多个非线性方程的解

时间:2020-07-25 13:09:17

标签: r equation

我想使用非线性方程的“ fsolve”函数解,方程和代码如下,但是我只能使用“ fsolve”函数来找到一组非线性方程的解,例如,我有A和B系数中的三个数字(A_coeff和B_coeff),根据我的想法,公式后的每个数字都会计算出一组解,那么三个,应该有三组解,我该怎么做< / p>

A_coeff<-c(177506.9,177639.3,178039.4)
B_coeff<-c(0.0003485474,0.0005155126,0.0004671370)
C_coeff<-5.511464
D_coeff<-23.39138
E_coeff<-5.0866e+17
F_coeff<-0.9732414
library('pracma')
Para_fun <- function(temp1) {
  new <- sqrt((4*temp1-1)/3)
  return(new)
}
Para_fun2<- function(temp1) {
  new2 <- ceiling(temp1/C_coeff)
  return(new2)
}
F_try<- function(x){
  s_actual <- x[1]
  K_actual <- x[2]
  n_tube <- x[3]
  c( A_coeff/K_actual-s_actual,
     (B_coeff+F_coeff/(E_coeff/Para_fun(n_tube)^(2/3))^0.25)^-1-K_actual,
     Para_fun2(s_actual)*D_coeff-n_tube)}
x0_xinitial_value<- c(20,2000,20)
X_result<- fsolve(F_try, x0_xinitial_value)
X_result$x 

1 个答案:

答案 0 :(得分:0)

解决问题的最简单方法是使用循环来求解A_coeffB_coeff每对的方程组。

将函数F_try重新定义为(我在这里重写了代码,以使其更易于阅读且不致混淆)

F_try<- function(x,k){
  s_actual <- x[1]
  K_actual <- x[2]
  n_tube <- x[3]
  y <- numeric(length(x))
  y[1] <- A_coeff[k]/K_actual-s_actual
  y[2] <- (B_coeff[k]+F_coeff/(E_coeff/Para_fun(n_tube)^(2/3))^0.25)^-1-K_actual
  y[3] <- Para_fun2(s_actual)*D_coeff-n_tube

y }

自变量k是系数A_coeffB_coeff的向量的索引。

如果您这样尝试

X_result <- matrix(NA,nrow=3,ncol=3)
xstart <- x0_xinitial_value
for( k in 1:3){
    z <- fsolve(F_try, xstart,k=k)
    X_result[k,] <- z$x
}
X_result

您会收到一条错误消息

Error in if (norm(s, "F") < tol || norm(as.matrix(ynew), "F") < tol) break : 

有消息

  missing value where TRUE/FALSE needed
Calls: fsolve -> broyden
In addition: Warning message:
In sqrt((4 * temp1 - 1)/3) : NaNs produced
Execution halted

目前尚不清楚问题出在哪里以及错误发生的原因。

还有另一个软件包nleqslv,可以提供更多有关发生问题的信息。

您可以像这样使用它

library(nleqslv)
X_result <- matrix(NA,nrow=3,ncol=3)
xstart <- x0_xinitial_value
for( k in 1:3){
    z <- nleqslv(xstart,F_try,k=k)
    X_result[k,] <- z$x
}
X_result

检查X_result表明第三种解决方案很可能是错误的。 简而言之,似乎对于k=3和您提供的算法的起始值找不到解决方案。

一个解决方案是使每个k的起始值等于前一个k的解决方案。像这样

X_result <- matrix(NA,nrow=3,ncol=3)
xstart <- x0_xinitial_value
for( k in 1:3){
    z <- nleqslv(xstart,F_try,k=k)
    X_result[k,] <- z$x
    xstart <- z$x
}
X_result

导致

          [,1]     [,2]     [,3]
[1,]  72.60480 2444.837 327.4793
[2,] 102.59563 1731.451 444.4362
[3,]  94.16426 1890.732 421.0448

建议为此矩阵的每一行检查nleqslv的退出代码 以确保找到解决方案。