Skip to article frontmatterSkip to article content
Site not loading correctly?

This may be due to an incorrect BASE_URL configuration. See the MyST Documentation for reference.

HybridNonlinearFactor

Open In Colab

A HybridNonlinearFactor represents a factor in a nonlinear hybrid optimization problem. Similar to HybridGaussianFactor, it represents a factor whose behavior depends on the assignment of discrete variables, but here the underlying components are gtsam.NonlinearFactors (specifically, NoiseModelFactors). It inherits from HybridFactor.

Mathematically, it represents a factor ϕ(X,M)\phi(X, M) whose value for a specific discrete assignment M=mM=m is proportional to the likelihood of the continuous variables XX under that mode, potentially weighted:

ϕ(X,M=m)∝exp⁡(−Em−12∣∣hm(X)−zm∣∣Σm2)\phi(X, M=m) \propto \exp\left(-E_m - \frac{1}{2} ||h_m(X) - z_m||^2_{\Sigma_m}\right)

This corresponds to an error (negative log-likelihood) for mode mm of:

error(X,M=m)=Em+12∣∣hm(X)−zm∣∣Σm2\text{error}(X, M=m) = E_m + \frac{1}{2} ||h_m(X) - z_m||^2_{\Sigma_m}

where for each discrete assignment mm, we have:

  • A nonlinear measurement function hm(X)h_m(X).

  • A measurement zmz_m.

  • A noise model Σm\Sigma_m defining the squared Mahalanobis distance ∣∣⋅∣∣Σm2|| \cdot ||^2_{\Sigma_m}.

  • An optional scalar term EmE_m. This term is added to the negative log-likelihood derived from the NoiseModelFactor. It can be used, for example, to incorporate prior probabilities P(m)P(m) for different modes by setting Em=−log⁡P(m)E_m = -\log P(m) (plus any constant, as only differences in EmE_m matter for optimization). A smaller EmE_m makes mode mm relatively more likely, all else being equal.

Internally, it uses a DecisionTree<Key, NonlinearFactorValuePair> to store the different nonlinear factor components (NoiseModelFactor::shared_ptr) and their associated scalar terms (double), indexed by the DiscreteKeys.

Initialization

Initialize with discrete keys and corresponding NoiseModelFactor components, optionally with scalar energies.

HybridNonlinearFactor (factors only):
HybridNonlinearFactor
 Hybrid [x0 x1; d0]
HybridNonlinearFactor
 Choice(d0) 
 0 Leaf (0) BetweenFactor(x0,x1)
  measured:  (1, 0, 0)
  noise model: diagonal sigmas [0.5; 0.5; 0.174532925];

 1 Leaf (0) BetweenFactor(x0,x1)
  measured:  (1, 0, 0)
  noise model: diagonal sigmas [0.1; 0.1; 0.0174532925];


HybridNonlinearFactor (factors + scalars):
HybridNonlinearFactor
 Hybrid [x0 x1; d0]
HybridNonlinearFactor
 Choice(d0) 
 0 Leaf (1.60943791) BetweenFactor(x0,x1)
  measured:  (1, 0, 0)
  noise model: diagonal sigmas [0.5; 0.5; 0.174532925];

 1 Leaf (0.223143551) BetweenFactor(x0,x1)
  measured:  (1, 0, 0)
  noise model: diagonal sigmas [0.1; 0.1; 0.0174532925];

Accessing Components and Error Calculation

Similar to HybridGaussianFactor, you can access the underlying decision tree and calculate errors.


Error for D0=0 (Slip): 1.6694379124341003
Error using HybridValues (Slip): 1.6694379124341003

Error for D0=1 (Grippy): 3.2231435513142106

Error Tree Choice(d0) 
Error Tree 0 Leaf 1.6694379
Error Tree 1 Leaf 3.2231436

Linearization

A key function is linearize, which converts the HybridNonlinearFactor into a HybridGaussianFactor at a given linearization point (continuous Values).


Linearized HybridGaussianFactor:
HybridGaussianFactor

Hybrid [x0 x1; d0]{
 Choice(d0) 
 0 Leaf :
  A[x0] = [
	-2, -0, -0;
	0, -2, -2;
	-0, -0, -5.72957795
]
  A[x1] = [
	2, 0, 0;
	0, 2, 0;
	0, 0, 5.72957795
]
  b = [ -0 -0 -0 ]
  No noise model
scalar: 1.23431728

 1 Leaf :
  A[x0] = [
	-10, -0, -0;
	0, -10, -10;
	-0, -0, -57.2957795
]
  A[x1] = [
	10, 0, 0;
	0, 10, 0;
	0, 0, 57.2957795
]
  b = [ -0 -0 -0 ]
  No noise model
scalar: -5.673438

}

Restriction (restrict)

Fixes the discrete variables, returning the corresponding NoiseModelFactor component.


Restricted Factor for D0=1 (Grippy):BetweenFactor(x0,x1)
  measured:  (1, 0, 0)
  noise model: diagonal sigmas [0.1; 0.1; 0.0174532925];