模块 Jacobian

require ‘bigdecimal/jacobian’

提供计算一组方程在点 x 处的 Jacobian 矩阵的方法。在以下方法中

f 是一个用于计算方程的 Jacobian 矩阵的对象。它必须提供以下方法

f.values(x)

返回所有函数在 x 处的取值

f.zero

返回 0.0

f.one

返回 1.0

f.two

返回 2.0

f.ten

返回 10.0

f.eps

返回用于确定两个值是否相等的收敛标准(epsilon 值)。如果 |a-b| < epsilon,则这两个值被认为相等。

x 是计算 Jacobian 的点。

fx 是 f.values(x)。

公共实例方法

dfdxi(f,fx,x,i) 点击切换源代码

计算 f[i]x[i] 处的导数。fxfx 处的取值。

# File bigdecimal/lib/bigdecimal/jacobian.rb, line 47
def dfdxi(f,fx,x,i)
  nRetry = 0
  n = x.size
  xSave = x[i]
  ok = 0
  ratio = f.ten*f.ten*f.ten
  dx = x[i].abs/ratio
  dx = fx[i].abs/ratio if isEqual(dx,f.zero,f.zero,f.eps)
  dx = f.one/f.ten     if isEqual(dx,f.zero,f.zero,f.eps)
  until ok>0 do
    deriv = []
    nRetry += 1
    if nRetry > 100
      raise "Singular Jacobian matrix. No change at x[" + i.to_s + "]"
    end
    dx = dx*f.two
    x[i] += dx
    fxNew = f.values(x)
    for j in 0...n do
      if !isEqual(fxNew[j],fx[j],f.zero,f.eps) then
        ok += 1
        deriv <<= (fxNew[j]-fx[j])/dx
      else
        deriv <<= f.zero
      end
    end
    x[i] = xSave
  end
  deriv
end
isEqual(a,b,zero=0.0,e=1.0e-8) 点击切换源代码

通过与零比较或使用 epsilon 值来确定两个数字的相等性

# File bigdecimal/lib/bigdecimal/jacobian.rb, line 30
def isEqual(a,b,zero=0.0,e=1.0e-8)
  aa = a.abs
  bb = b.abs
  if aa == zero &&  bb == zero then
    true
  else
    if ((a-b)/(aa+bb)).abs < e then
      true
    else
      false
    end
  end
end
jacobian(f,fx,x) 点击切换源代码

计算 fx 处的 Jacobianfxfx 处的取值。

# File bigdecimal/lib/bigdecimal/jacobian.rb, line 79
def jacobian(f,fx,x)
  n = x.size
  dfdx = Array.new(n*n)
  for i in 0...n do
    df = dfdxi(f,fx,x,i)
    for j in 0...n do
      dfdx[j*n+i] = df[j]
    end
  end
  dfdx
end