logo资料库

最小二乘法拟合原理及代码实现.pdf

第1页 / 共8页
第2页 / 共8页
第3页 / 共8页
第4页 / 共8页
第5页 / 共8页
第6页 / 共8页
第7页 / 共8页
第8页 / 共8页
资料共8页,全文预览结束
最小二乘法拟合原理及代码实现                        1. 最小二乘法定义  已知一组实验数据(xi, yi  )(i  =  0,1,2,….,m),且观测数据有误差 求自变量 x 与因变量 y 之间的函数关系 y = F(x),不要求 y = F(x)经过 所有点,而只要求在给定点的误差  δi = F(xi) – yi (i = 0,1,2,…,m)  按某种标准最小。  度量的标准不同,将导致不同的结果,常用的准则有如下三 种:  a. 残差的最大绝对值为最小  max 0 i m   |  i |  max 0 i m   | y F x ( i i  ) | min    b. 残差的绝对值之和最小  m  i  0 |  i |  m  i  0 y F x | ( i i  ) | min    c. 残差的平方和最小  m   2  i  m i  0 i  0 ( y F x ( i i  2 )) min    其中 c 被称为最小二乘法原则。  具体定义:已知一组数据(xi,  yi  )(i  =  0,1,2,….,m),在函数类  span {1, x ,...., x }n 中找到一个函数 y  S x *( ) ,是误差平方和最小,即:  m m   2  i  i  0 i  0 S x ( ( ) *  y i 2 )  min S x ( )   m  i  0 S x ( ( )  y i 2 )   这里: S x ( )  a 0  a x 1  ......  n a x n     (n
  求最小二乘解 y  S x *( ) 的方法    现要求一 S x ( ) n   使得:  a x k k n k  0 I  m  i  0 S x [ ( ) n  y i ] 2  n m   [ i  0 k  0 k a x k i  y i ] min 2      显然 I  n m   [ i  0 k  0 k a x k i  y i ] 2 为 0 a a , 1 ( ,...., a 的多元函数,因此上述问题 )n 即为求 I  I a a ( , 1 0 ,...., a )n 的极值问题。  多元函数的求极值的必要条件:设函数 z=f(x,y)在点(x0,y0)具有 偏导数,且在点(x0,y0)有极值,则它在该点的偏导数必然为零。  由上述定理得:  I  a  j  2 n m   ( i  0 k  0 a x k k i  y x ) k i i  0       (j = 0,1,2,….,n)  即: n m   ( k  0 i  0  j x k i ) a k             (j = 0,1,2,….,n)  x y j i i m i  0 上式是关于 0 a a , 1 ( ,...., a 的线性方程组,用矩阵表示为:  )n m m m x i x 2 i  0 i  m  i  0 1 x i m   m             0 0 i i m    x n i m  x n i 1  i  0    x n i 1  x n i  0 i  m  i  0 m   x 2 i i  0 n            a 0 a 1  a n                         y i  0 i  m  i  0 x y i i  x y n i i m  i  0              可以证明,方程组的系数矩阵式一个对称正定矩阵,故存在唯一解。 
令 X m  0 i  m  i  0 x i x 2 i 1 x i m   m              0 0 i i m    x n i m  x n i 1  i  0    m  0 i  m  i  0 x n i 1  x n i m   x 2 i i  0 n            A  , a 0 a 1  a n             Y ,             m  0 i  m  i  0 m  i  0 y i x y i i  x y n i i ,则             XA Y   1  X XA X Y 1     EA X Y 1    A X Y 1  其中 1X  是 X 的逆矩阵, E 是单位矩阵。  。可以算出 0 a a , 1 ( ,...., a 。  )n         还可以用消元法算出 0 a a , 1 ( ,...., a ,程序代码一般是用消元法算出 )n 系数的。  2. 直线拟合  曲线拟合中最基本和最常用的是直线拟合。设 x和 y之间的 函数关系由直线方程 y=a0+a1x  给出。式中有两个待定参数,a0代表截距,a1代表斜率。对于等精 度测量所得到的 m 组数据(xi,yi),i=1,2……,m,xi值被认为 是准确的,所有的误差只联系着 yi。      下面利用最小二乘法把观测数据拟合为直线。要求残差的平方 和最小,即 应有  a  0  a  1 m  0 i  m  i  0 m  i  0 y i     a 0  a x i 1  2     y i     a 0  a x i 1 2    2    y i     a 0  a x i 1 2    2   m 0 i  m  i  0  y i  a 0  a x i 1   0    y i  a 0  a x i 1   0
整理得       a m a  1 0  a x a   i 0 1 x  i     x y x 2 i i i y i       解方程,得   a 0  x 2 i         x y  i i       m x x 2  i i      x y x y  i i i       x x 2  i i  m  2 m  x y i i  a 1  i 2 C#程序代码的实现:  return false; double fmX = 0.0; double fmY = 0.0; double fmXX = 0.0; double fmXY = 0.0; double fn = 0.0; if( 0 == mapFoldList.Count) { } bool fnCalculateLineKB(ref List mapFoldList,ref double fk,ref double fb) { foreach (sAD_PWR iter in mapFoldList) { fmX += iter.fAD; fmY += iter.fPWR; fmXX += iter.fAD * iter.fAD; fmXY += iter.fAD * iter.fPWR; long lCount = mapFoldList.Count; if(lCount < 2) { } return false; fn = lCount;
if(Math.Abs(fmX * fmX - fmXX * fn) < 0.000001) { } return false; } fk = (fmY * fmX - fmXY * fn)/(fmX * fmX - fmXX * fn); fb = (fmY - fmX * fk)/fn; return true; // Function : fnCurveSimulate(double n[], double T[], int M, int N,int } 3. 曲线拟合(三阶及以上曲线)代码实现  根据 XA Y 得出,我们需要算出矩阵 X 和矩阵Y ,再对 X 进行矩阵 变换,得到消元后的矩阵,算出 0 a a 1, ,...., a 。代码的实现:  n ///////////////////////////////////////////////////////////////// // ParaIn : n[] 自变量数据数组 // T[] 因变量数据数组 // M 拟合公式的最高阶数 // N 数据组数 // xi 所返回系数值的对应参数 // ParaOut : 无 // Return : double // Description : 用于最小二乘法曲线拟合 ///////////////////////////////////////////////////////////////// ///// xi) ////// int N,int xi) { double [,]b = new double[10,20]; double [,]A = new double[10,10]; double []B = new double[10]; double []x = new double[10]; double []y = new double[10]; public static double fnCurveSimulate(double []n, double []T, int M,
for(j=0; j
//开始进行消元运算 for(i=1; i
} //得出阶数最高位的系数 x[M-1]=y[M-1]/A[M-1,M-1]; for(i=M-2; i>=0; i--) { } t=0; for(j=i+1; j
分享到:
收藏