如何使用R语言编写牛顿插值公式对缺失值进行插值

Python024

如何使用R语言编写牛顿插值公式对缺失值进行插值,第1张

LagrangePolynomial <- function(x,y) {

  len = length(x)

  if(len != length(y))

    stop("length not equal!")

   

  if(len < 2)

    stop("dim size must more than 1")

   

  #pretreat data abd alloc memery

  xx <- paste("(","a -",x,")")

  m <- c(rep(0,len))

   

  #combin express

  for(i in 1:len) {

    td <- 1

    tm <- "1"

    for(j in 1:len) {

      if(i != j) {

        td <- td*(x[i] - x[j])

        tm <- paste(tm,"*",xx[j])

      }

    }

    tm <- paste(tm,"/",td)

    m[i]<-tm #m[i] <- parse(text=tm)

  }

   

  #combin the exrpession

  m <- paste(m,"*",y)

  r <- paste(m,collapse="+")

   

  #combin the function

  fbody <- paste("{ return(",r,")}")

  f <- function(a) {}

   

  #fill the function's body

  body(f) <- parse(text=fbody)

   

  return(f)

}

这是拉格朗日多项式插值算法  你参考下吧

第一步是把“I”弄出来(如下图)。

这相当于以红色橙色为顶面和底面,在四个侧面拼出四条竖线。这一步非常简单,可以自己尝试。不过也有一步做成的公式不妨参考参考:(R2 F2 R2) (L2 F2 L2) 。要说明一下,这个公式只要确保红色面和橙色面其中一个为顶面,另一个为底面就行了,更具体的方向还要看第二步。

第二步是把U弄出来,如下图。

你会发现,要做“U”的话,底下还缺一个黄色的棱块。因为这个“I Love You”的图形是三面的,所以剩下三面可以不用管它。这样的话,有些方块是可以借用的。那么我们就来借用一下。把人魔方翻过来,如下图。

把橙色朝上,绿色朝前,黄色朝左。黄色面、绿色面、橙色面是在图形的背面,因此橙黄棱块可以——也是应该——被移到橙白棱块的位置,根据魔方的位置。这样刚还既完成了“U”,也没有动到“I”。这个移动就是三阶魔方层先法的棱归位或者CFOP手法里的PLL。那这个就很好搞定了,层先第七步公式做两次,或者其逆公式(CFOP)做一次就行了。顺便说一下公式:R2 U (R U R' U') R' U' R' U R'。

顺便提醒一下,千万要看准,不然就做成“You Love I”了!(如下图)

做完第二步,你会发现距离完成只有一个红色角块的事情了(如下图)。

最后一步就是要把红色顶面那个角块翻转一下,使其朝上的不为红色,这样一个缺口就能表示心形了。做这一步要用到一条重要的公式,因此方向绝对不能错。其方向是绿色面朝前,蓝色面朝后,红色超右,橙色朝左,白色朝上,黄色朝下。

对好了,然后就做公式。这个公式是用来盲拧的,叫做“8位顺转,5位逆转”。且不管它究竟是什么,照做便是,具体效果可以慢慢研究:(R U R' U') (R U R' D) (R U' R' U) (R U' R' D')。(效果如上图)

其实,如果怕搞乱的话,可以一个公式搞定所有步骤。首先确定橙色面朝上,红色面朝下,绿色面朝前,蓝色面朝后,白色面朝右,黄色面朝左,然后做这个公式就可以了:L2 F2 L2 R2 F2 U (R U R' U') R' U' R' U R' z' (R U R' U') (R U R' D) (R U' R' U) (R U' R' D')。“ z' ”前面可以算是第一步和第二步的组合变形,后面就是“8位顺转,5位逆转”。

好了,这样一个“I Love You”的图形就拼好了。

最简单但计算量最大的是泰勒公式:e=1+1/1!+1/2!+1/3!+1/4!+...

下面是求e的R语言函数:

e_fun <- function(n) {

  etemp <- 1

  ni <- 1L

  for (i in 1:n) {

    etemp <- etemp + 1 / ni

    ni <- ni * (i + 1)

  }

  return(etemp)

}

不过你题目中要求的是求到精度为0.00001就停止,所以可以采用repeat循环:

i <- 1L

ni <- 1L

etemp <- 1

repeat {

  etemp1 <- etemp

  etemp <- etemp + 1 / ni

  ni <- ni * (i + 1)

  i <- i + 1

  if (etemp - etemp1 < 0.00001) break

}

i

etemp

在最后可以看到,求到i=10时,精度就已经达到要求了。