test_KarcherMeanFactor.py
Go to the documentation of this file.
1 """
2 GTSAM Copyright 2010-2019, Georgia Tech Research Corporation,
3 Atlanta, Georgia 30332-0415
4 All Rights Reserved
5 
6 See LICENSE for the license information
7 
8 KarcherMeanFactor unit tests.
9 Author: Frank Dellaert
10 """
11 
12 # pylint: disable=invalid-name, no-name-in-module, no-member
13 
14 import unittest
15 
16 import gtsam
17 import numpy as np
18 from gtsam.utils.test_case import GtsamTestCase
19 
20 KEY = 0
22 
23 
24 def find_Karcher_mean_Rot3(rotations):
25  """Find the Karcher mean of given values."""
26  # Cost function C(R) = \sum PriorFactor(R_i)::error(R)
27  # No closed form solution.
29  for R in rotations:
30  graph.add(gtsam.PriorFactorRot3(KEY, R, MODEL))
31  initial = gtsam.Values()
32  initial.insert(KEY, gtsam.Rot3())
33  result = gtsam.GaussNewtonOptimizer(graph, initial).optimize()
34  return result.atRot3(KEY)
35 
36 
37 # Rot3 version
38 R = gtsam.Rot3.Expmap(np.array([0.1, 0, 0]))
39 
40 
42 
43  def test_find(self):
44  # Check that optimizing for Karcher mean (which minimizes Between distance)
45  # gets correct result.
46  rotations = {R, R.inverse()}
47  expected = gtsam.Rot3()
48  actual = find_Karcher_mean_Rot3(rotations)
49  self.gtsamAssertEquals(expected, actual)
50 
51  def test_factor(self):
52  """Check that the InnerConstraint factor leaves the mean unchanged."""
53  # Make a graph with two variables, one between, and one InnerConstraint
54  # The optimal result should satisfy the between, while moving the other
55  # variable to make the mean the same as before.
56  # Mean of R and R' is identity. Let's make a BetweenFactor making R21 =
57  # R*R*R, i.e. geodesic length is 3 rather than 2.
59  R12 = R.compose(R.compose(R))
60  graph.add(gtsam.BetweenFactorRot3(1, 2, R12, MODEL))
61  keys = gtsam.KeyVector()
62  keys.append(1)
63  keys.append(2)
64  graph.add(gtsam.KarcherMeanFactorRot3(keys))
65 
66  initial = gtsam.Values()
67  initial.insert(1, R.inverse())
68  initial.insert(2, R)
69  expected = find_Karcher_mean_Rot3([R, R.inverse()])
70 
71  result = gtsam.GaussNewtonOptimizer(graph, initial).optimize()
72  actual = find_Karcher_mean_Rot3(
73  [result.atRot3(1), result.atRot3(2)])
74  self.gtsamAssertEquals(expected, actual)
75  self.gtsamAssertEquals(
76  R12, result.atRot3(1).between(result.atRot3(2)))
77 
78 
79 if __name__ == "__main__":
80  unittest.main()
T between(const T &t1, const T &t2)
Definition: lieProxies.h:36
def gtsamAssertEquals(self, actual, expected, tol=1e-9)
Definition: test_case.py:18
static shared_ptr Create(size_t dim)
Definition: NoiseModel.h:608
FastVector< Key > KeyVector
Define collection type once and for all - also used in wrappers.
Definition: Key.h:86
static Rot3 Expmap(const Vector3 &v, OptionalJacobian< 3, 3 > H=boost::none)
Definition: Rot3.h:377
int optimize(const SfmData &db, const NonlinearFactorGraph &graph, const Values &initial, bool separateCalibration=false)
Definition: timeSFMBAL.h:63
def find_Karcher_mean_Rot3(rotations)


gtsam
Author(s):
autogenerated on Sat May 8 2021 02:46:03