Fixed noisemodel compile error, moved remaining nonlinear constraints to NonlinearEquality
parent
98410ca5c9
commit
0fe13ae3ca
221
.cproject
221
.cproject
|
@ -375,14 +375,6 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
<target name="testGaussianFactor.run" path="linear/tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>testGaussianFactor.run</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="all" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="all" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -409,6 +401,7 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="tests/testBayesTree.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="tests/testBayesTree.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments/>
|
||||||
<buildTarget>tests/testBayesTree.run</buildTarget>
|
<buildTarget>tests/testBayesTree.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -416,6 +409,7 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testBinaryBayesNet.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testBinaryBayesNet.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments/>
|
||||||
<buildTarget>testBinaryBayesNet.run</buildTarget>
|
<buildTarget>testBinaryBayesNet.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -463,6 +457,7 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testSymbolicBayesNet.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testSymbolicBayesNet.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments/>
|
||||||
<buildTarget>testSymbolicBayesNet.run</buildTarget>
|
<buildTarget>testSymbolicBayesNet.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -470,6 +465,7 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="tests/testSymbolicFactor.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="tests/testSymbolicFactor.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments/>
|
||||||
<buildTarget>tests/testSymbolicFactor.run</buildTarget>
|
<buildTarget>tests/testSymbolicFactor.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -477,6 +473,7 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testSymbolicFactorGraph.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testSymbolicFactorGraph.run" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments/>
|
||||||
<buildTarget>testSymbolicFactorGraph.run</buildTarget>
|
<buildTarget>testSymbolicFactorGraph.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -492,11 +489,20 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="tests/testBayesTree" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="tests/testBayesTree" path="inference" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments/>
|
||||||
<buildTarget>tests/testBayesTree</buildTarget>
|
<buildTarget>tests/testBayesTree</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
|
<target name="testGaussianFactor.run" path="linear/tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>testGaussianFactor.run</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
<target name="check" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="check" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -523,7 +529,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testGraph.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testGraph.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testGraph.run</buildTarget>
|
<buildTarget>testGraph.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -595,7 +600,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testInference.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testInference.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testInference.run</buildTarget>
|
<buildTarget>testInference.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -603,7 +607,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testGaussianFactor.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testGaussianFactor.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testGaussianFactor.run</buildTarget>
|
<buildTarget>testGaussianFactor.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -611,7 +614,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testJunctionTree.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testJunctionTree.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testJunctionTree.run</buildTarget>
|
<buildTarget>testJunctionTree.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -619,7 +621,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testSymbolicBayesNet.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testSymbolicBayesNet.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testSymbolicBayesNet.run</buildTarget>
|
<buildTarget>testSymbolicBayesNet.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -627,7 +628,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testSymbolicFactorGraph.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testSymbolicFactorGraph.run" path="tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testSymbolicFactorGraph.run</buildTarget>
|
<buildTarget>testSymbolicFactorGraph.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -681,22 +681,6 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
<target name="all" path="CppUnitLite" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>all</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="clean" path="CppUnitLite" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>clean</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="tests/testPose2.run" path="build_retract/gtsam/geometry" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="tests/testPose2.run" path="build_retract/gtsam/geometry" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -713,6 +697,22 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
|
<target name="all" path="CppUnitLite" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>all</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
|
<target name="clean" path="CppUnitLite" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>clean</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
<target name="all" path="spqr_mini" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="all" path="spqr_mini" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -737,7 +737,15 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
<target name="check" path="build/gtsam/nonlinear" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="all" path="build_wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>all</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
|
<target name="check" path="build_wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
<buildTarget>check</buildTarget>
|
<buildTarget>check</buildTarget>
|
||||||
|
@ -745,6 +753,14 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
|
<target name="clean" path="build_wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>clean</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
<target name="tests/testGeneralSFMFactor.run" path="build/gtsam/slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="tests/testGeneralSFMFactor.run" path="build/gtsam/slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -785,15 +801,7 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
<target name="all" path="build_wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="check" path="build/gtsam/nonlinear" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>all</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="check" path="build_wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
<buildTarget>check</buildTarget>
|
<buildTarget>check</buildTarget>
|
||||||
|
@ -801,14 +809,6 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
<target name="clean" path="build_wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>clean</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="check" path="build/geometry" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="check" path="build/geometry" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -1033,14 +1033,6 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
<target name="testNonlinearEqualityConstraint.run" path="build/tests" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>testNonlinearEqualityConstraint.run</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="SimpleRotation.run" path="examples" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="SimpleRotation.run" path="examples" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -1139,6 +1131,7 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testErrors.run" path="linear" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testErrors.run" path="linear" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments/>
|
||||||
<buildTarget>testErrors.run</buildTarget>
|
<buildTarget>testErrors.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -1546,7 +1539,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testSimulated2DOriented.run" path="slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testSimulated2DOriented.run" path="slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testSimulated2DOriented.run</buildTarget>
|
<buildTarget>testSimulated2DOriented.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -1586,7 +1578,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testSimulated2D.run" path="slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testSimulated2D.run" path="slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testSimulated2D.run</buildTarget>
|
<buildTarget>testSimulated2D.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -1594,7 +1585,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="testSimulated3D.run" path="slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testSimulated3D.run" path="slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>testSimulated3D.run</buildTarget>
|
<buildTarget>testSimulated3D.run</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -1842,7 +1832,6 @@
|
||||||
</target>
|
</target>
|
||||||
<target name="tests/testGaussianISAM2" path="build/slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="tests/testGaussianISAM2" path="build/slam" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments/>
|
|
||||||
<buildTarget>tests/testGaussianISAM2</buildTarget>
|
<buildTarget>tests/testGaussianISAM2</buildTarget>
|
||||||
<stopOnError>true</stopOnError>
|
<stopOnError>true</stopOnError>
|
||||||
<useDefaultCommand>false</useDefaultCommand>
|
<useDefaultCommand>false</useDefaultCommand>
|
||||||
|
@ -1864,6 +1853,46 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
|
<target name="install" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>install</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
|
<target name="clean" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>clean</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
|
<target name="check" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>check</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
|
<target name="all" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>all</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
|
<target name="dist" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>dist</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
<target name="testRot3.run" path="geometry" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="testRot3.run" path="geometry" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -1960,62 +1989,6 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
<target name="install" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>install</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="clean" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>clean</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="check" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>check</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="all" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>all</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="dist" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>dist</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="check" path="build/wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>check</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="install" path="build/wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
|
||||||
<buildCommand>make</buildCommand>
|
|
||||||
<buildArguments>-j2</buildArguments>
|
|
||||||
<buildTarget>install</buildTarget>
|
|
||||||
<stopOnError>true</stopOnError>
|
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
|
||||||
<runAllBuilders>true</runAllBuilders>
|
|
||||||
</target>
|
|
||||||
<target name="check" path="build" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
<target name="check" path="build" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
<buildCommand>make</buildCommand>
|
<buildCommand>make</buildCommand>
|
||||||
<buildArguments>-j2</buildArguments>
|
<buildArguments>-j2</buildArguments>
|
||||||
|
@ -2056,6 +2029,22 @@
|
||||||
<useDefaultCommand>true</useDefaultCommand>
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
<runAllBuilders>true</runAllBuilders>
|
<runAllBuilders>true</runAllBuilders>
|
||||||
</target>
|
</target>
|
||||||
|
<target name="check" path="build/wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>check</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
|
<target name="install" path="build/wrap" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||||
|
<buildCommand>make</buildCommand>
|
||||||
|
<buildArguments>-j2</buildArguments>
|
||||||
|
<buildTarget>install</buildTarget>
|
||||||
|
<stopOnError>true</stopOnError>
|
||||||
|
<useDefaultCommand>true</useDefaultCommand>
|
||||||
|
<runAllBuilders>true</runAllBuilders>
|
||||||
|
</target>
|
||||||
</buildTargets>
|
</buildTargets>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
</cproject>
|
</cproject>
|
||||||
|
|
|
@ -296,8 +296,6 @@ void Constrained::print(const std::string& name) const {
|
||||||
|
|
||||||
/* ************************************************************************* */
|
/* ************************************************************************* */
|
||||||
Vector Constrained::whiten(const Vector& v) const {
|
Vector Constrained::whiten(const Vector& v) const {
|
||||||
// ediv_ does the right thing with the errors
|
|
||||||
// return ediv_(v, sigmas_);
|
|
||||||
const Vector& a = v;
|
const Vector& a = v;
|
||||||
const Vector& b = sigmas_;
|
const Vector& b = sigmas_;
|
||||||
size_t n = a.size();
|
size_t n = a.size();
|
||||||
|
@ -305,7 +303,7 @@ Vector Constrained::whiten(const Vector& v) const {
|
||||||
Vector c(n);
|
Vector c(n);
|
||||||
for( size_t i = 0; i < n; i++ ) {
|
for( size_t i = 0; i < n; i++ ) {
|
||||||
const double& ai = a(i), &bi = b(i);
|
const double& ai = a(i), &bi = b(i);
|
||||||
c(i) = (bi==0.0) ? ai : ai/bi;
|
c(i) = (bi==0.0) ? ai : ai/bi; // NOTE: not ediv_()
|
||||||
}
|
}
|
||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
|
@ -313,6 +311,7 @@ Vector Constrained::whiten(const Vector& v) const {
|
||||||
/* ************************************************************************* */
|
/* ************************************************************************* */
|
||||||
double Constrained::distance(const Vector& v) const {
|
double Constrained::distance(const Vector& v) const {
|
||||||
Vector w = Diagonal::whiten(v); // get noisemodel for constrained elements
|
Vector w = Diagonal::whiten(v); // get noisemodel for constrained elements
|
||||||
|
// TODO Find a better way of doing these checks
|
||||||
for (size_t i=0; i<dim_; ++i) { // add mu weights on constrained variables
|
for (size_t i=0; i<dim_; ++i) { // add mu weights on constrained variables
|
||||||
if (isinf(w[i])) // whiten makes constrained variables infinite
|
if (isinf(w[i])) // whiten makes constrained variables infinite
|
||||||
w[i] = v[i] * sqrt(mu_[i]); // TODO: may want to store sqrt rather than rebuild
|
w[i] = v[i] * sqrt(mu_[i]); // TODO: may want to store sqrt rather than rebuild
|
||||||
|
@ -322,15 +321,6 @@ double Constrained::distance(const Vector& v) const {
|
||||||
return w.dot(w);
|
return w.dot(w);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
double Constrained::distance(const Vector& v) const {
|
|
||||||
Vector w = whiten(v); // get noisemodel for constrained elements
|
|
||||||
for (size_t i=0; i<dim_; ++i) // add mu weights on constrained variables
|
|
||||||
if (isinf(w[i])) // whiten makes constrained variables infinite
|
|
||||||
w[i] = v[i] * sqrt(mu_[i]); // FIXME: may want to store sqrt rather than rebuild
|
|
||||||
return w.dot(w);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
/* ************************************************************************* */
|
||||||
Matrix Constrained::Whiten(const Matrix& H) const {
|
Matrix Constrained::Whiten(const Matrix& H) const {
|
||||||
// selective scaling
|
// selective scaling
|
||||||
|
@ -432,7 +422,7 @@ SharedDiagonal Constrained::QR(Matrix& Ab) const {
|
||||||
}
|
}
|
||||||
toc(4, "constrained_QR write back into Ab");
|
toc(4, "constrained_QR write back into Ab");
|
||||||
|
|
||||||
// Must include mus, as the defaults might be higher, resulting in non-convergence
|
// Must include mu, as the defaults might be higher, resulting in non-convergence
|
||||||
return mixed ? Constrained::MixedPrecisions(mu_, precisions) : Diagonal::Precisions(precisions);
|
return mixed ? Constrained::MixedPrecisions(mu_, precisions) : Diagonal::Precisions(precisions);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -33,7 +33,7 @@ headers += ISAM2.h ISAM2-inl.h ISAM2-impl-inl.h
|
||||||
sources += GaussianISAM2.cpp
|
sources += GaussianISAM2.cpp
|
||||||
|
|
||||||
# Nonlinear constraints
|
# Nonlinear constraints
|
||||||
headers += NonlinearEquality.h NonlinearConstraint.h
|
headers += NonlinearEquality.h
|
||||||
|
|
||||||
# White noise factor
|
# White noise factor
|
||||||
headers += WhiteNoiseFactor.h
|
headers += WhiteNoiseFactor.h
|
||||||
|
|
|
@ -1,128 +0,0 @@
|
||||||
/* ----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
* GTSAM Copyright 2010, Georgia Tech Research Corporation,
|
|
||||||
* Atlanta, Georgia 30332-0415
|
|
||||||
* All Rights Reserved
|
|
||||||
* Authors: Frank Dellaert, et al. (see THANKS for the full author list)
|
|
||||||
|
|
||||||
* See LICENSE for the license information
|
|
||||||
|
|
||||||
* -------------------------------------------------------------------------- */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* @file NonlinearConstraint.h
|
|
||||||
* @brief Implements simple cases of constraints
|
|
||||||
* @author Alex Cunningham
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <gtsam/nonlinear/NonlinearFactor.h>
|
|
||||||
|
|
||||||
namespace gtsam {
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
/**
|
|
||||||
* Simple unary equality constraint - fixes a value for a variable
|
|
||||||
*/
|
|
||||||
template<class VALUES, class KEY>
|
|
||||||
class NonlinearEquality1 : public NonlinearFactor1<VALUES, KEY> {
|
|
||||||
|
|
||||||
public:
|
|
||||||
typedef typename KEY::Value X;
|
|
||||||
|
|
||||||
protected:
|
|
||||||
typedef NonlinearFactor1<VALUES, KEY> Base;
|
|
||||||
|
|
||||||
/** default constructor to allow for serialization */
|
|
||||||
NonlinearEquality1() {}
|
|
||||||
|
|
||||||
X value_; /// fixed value for variable
|
|
||||||
|
|
||||||
GTSAM_CONCEPT_MANIFOLD_TYPE(X);
|
|
||||||
GTSAM_CONCEPT_TESTABLE_TYPE(X);
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
typedef boost::shared_ptr<NonlinearEquality1<VALUES, KEY> > shared_ptr;
|
|
||||||
|
|
||||||
NonlinearEquality1(const X& value, const KEY& key1, double mu = 1000.0)
|
|
||||||
: Base(noiseModel::Constrained::All(value.dim(), fabs(mu)), key1), value_(value) {}
|
|
||||||
|
|
||||||
virtual ~NonlinearEquality1() {}
|
|
||||||
|
|
||||||
/** g(x) with optional derivative */
|
|
||||||
Vector evaluateError(const X& x1, boost::optional<Matrix&> H = boost::none) const {
|
|
||||||
if (H) (*H) = eye(x1.dim());
|
|
||||||
// manifold equivalent of h(x)-z -> log(z,h(x))
|
|
||||||
return value_.localCoordinates(x1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Print */
|
|
||||||
virtual void print(const std::string& s = "") const {
|
|
||||||
std::cout << s << ": NonlinearEquality1("
|
|
||||||
<< (std::string) this->key_ << "),"<< "\n";
|
|
||||||
this->noiseModel_->print();
|
|
||||||
value_.print("Value");
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
/** Serialization function */
|
|
||||||
friend class boost::serialization::access;
|
|
||||||
template<class ARCHIVE>
|
|
||||||
void serialize(ARCHIVE & ar, const unsigned int version) {
|
|
||||||
ar & boost::serialization::make_nvp("NonlinearFactor1",
|
|
||||||
boost::serialization::base_object<Base>(*this));
|
|
||||||
ar & BOOST_SERIALIZATION_NVP(value_);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
/**
|
|
||||||
* Simple binary equality constraint - this constraint forces two factors to
|
|
||||||
* be the same.
|
|
||||||
*/
|
|
||||||
template<class VALUES, class KEY>
|
|
||||||
class NonlinearEquality2 : public NonlinearFactor2<VALUES, KEY, KEY> {
|
|
||||||
public:
|
|
||||||
typedef typename KEY::Value X;
|
|
||||||
|
|
||||||
protected:
|
|
||||||
typedef NonlinearFactor2<VALUES, KEY, KEY> Base;
|
|
||||||
|
|
||||||
GTSAM_CONCEPT_MANIFOLD_TYPE(X);
|
|
||||||
|
|
||||||
/** default constructor to allow for serialization */
|
|
||||||
NonlinearEquality2() {}
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
typedef boost::shared_ptr<NonlinearEquality2<VALUES, KEY> > shared_ptr;
|
|
||||||
|
|
||||||
NonlinearEquality2(const KEY& key1, const KEY& key2, double mu = 1000.0)
|
|
||||||
: Base(noiseModel::Constrained::All(X::Dim(), fabs(mu)), key1, key2) {}
|
|
||||||
virtual ~NonlinearEquality2() {}
|
|
||||||
|
|
||||||
/** g(x) with optional derivative2 */
|
|
||||||
Vector evaluateError(const X& x1, const X& x2,
|
|
||||||
boost::optional<Matrix&> H1 = boost::none,
|
|
||||||
boost::optional<Matrix&> H2 = boost::none) const {
|
|
||||||
const size_t p = X::Dim();
|
|
||||||
if (H1) *H1 = -eye(p);
|
|
||||||
if (H2) *H2 = eye(p);
|
|
||||||
return x1.localCoordinates(x2);
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
/** Serialization function */
|
|
||||||
friend class boost::serialization::access;
|
|
||||||
template<class ARCHIVE>
|
|
||||||
void serialize(ARCHIVE & ar, const unsigned int version) {
|
|
||||||
ar & boost::serialization::make_nvp("NonlinearFactor2",
|
|
||||||
boost::serialization::base_object<Base>(*this));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
}
|
|
|
@ -154,7 +154,111 @@ namespace gtsam {
|
||||||
ar & BOOST_SERIALIZATION_NVP(error_gain_);
|
ar & BOOST_SERIALIZATION_NVP(error_gain_);
|
||||||
}
|
}
|
||||||
|
|
||||||
}; // NonlinearEquality
|
}; // \class NonlinearEquality
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
/**
|
||||||
|
* Simple unary equality constraint - fixes a value for a variable
|
||||||
|
*/
|
||||||
|
template<class VALUES, class KEY>
|
||||||
|
class NonlinearEquality1 : public NonlinearFactor1<VALUES, KEY> {
|
||||||
|
|
||||||
|
public:
|
||||||
|
typedef typename KEY::Value X;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
typedef NonlinearFactor1<VALUES, KEY> Base;
|
||||||
|
|
||||||
|
/** default constructor to allow for serialization */
|
||||||
|
NonlinearEquality1() {}
|
||||||
|
|
||||||
|
X value_; /// fixed value for variable
|
||||||
|
|
||||||
|
GTSAM_CONCEPT_MANIFOLD_TYPE(X);
|
||||||
|
GTSAM_CONCEPT_TESTABLE_TYPE(X);
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
typedef boost::shared_ptr<NonlinearEquality1<VALUES, KEY> > shared_ptr;
|
||||||
|
|
||||||
|
NonlinearEquality1(const X& value, const KEY& key1, double mu = 1000.0)
|
||||||
|
: Base(noiseModel::Constrained::All(value.dim(), fabs(mu)), key1), value_(value) {}
|
||||||
|
|
||||||
|
virtual ~NonlinearEquality1() {}
|
||||||
|
|
||||||
|
/** g(x) with optional derivative */
|
||||||
|
Vector evaluateError(const X& x1, boost::optional<Matrix&> H = boost::none) const {
|
||||||
|
if (H) (*H) = eye(x1.dim());
|
||||||
|
// manifold equivalent of h(x)-z -> log(z,h(x))
|
||||||
|
return value_.localCoordinates(x1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Print */
|
||||||
|
virtual void print(const std::string& s = "") const {
|
||||||
|
std::cout << s << ": NonlinearEquality1("
|
||||||
|
<< (std::string) this->key_ << "),"<< "\n";
|
||||||
|
this->noiseModel_->print();
|
||||||
|
value_.print("Value");
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
/** Serialization function */
|
||||||
|
friend class boost::serialization::access;
|
||||||
|
template<class ARCHIVE>
|
||||||
|
void serialize(ARCHIVE & ar, const unsigned int version) {
|
||||||
|
ar & boost::serialization::make_nvp("NonlinearFactor1",
|
||||||
|
boost::serialization::base_object<Base>(*this));
|
||||||
|
ar & BOOST_SERIALIZATION_NVP(value_);
|
||||||
|
}
|
||||||
|
}; // \NonlinearEquality1
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
/**
|
||||||
|
* Simple binary equality constraint - this constraint forces two factors to
|
||||||
|
* be the same.
|
||||||
|
*/
|
||||||
|
template<class VALUES, class KEY>
|
||||||
|
class NonlinearEquality2 : public NonlinearFactor2<VALUES, KEY, KEY> {
|
||||||
|
public:
|
||||||
|
typedef typename KEY::Value X;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
typedef NonlinearFactor2<VALUES, KEY, KEY> Base;
|
||||||
|
|
||||||
|
GTSAM_CONCEPT_MANIFOLD_TYPE(X);
|
||||||
|
|
||||||
|
/** default constructor to allow for serialization */
|
||||||
|
NonlinearEquality2() {}
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
typedef boost::shared_ptr<NonlinearEquality2<VALUES, KEY> > shared_ptr;
|
||||||
|
|
||||||
|
NonlinearEquality2(const KEY& key1, const KEY& key2, double mu = 1000.0)
|
||||||
|
: Base(noiseModel::Constrained::All(X::Dim(), fabs(mu)), key1, key2) {}
|
||||||
|
virtual ~NonlinearEquality2() {}
|
||||||
|
|
||||||
|
/** g(x) with optional derivative2 */
|
||||||
|
Vector evaluateError(const X& x1, const X& x2,
|
||||||
|
boost::optional<Matrix&> H1 = boost::none,
|
||||||
|
boost::optional<Matrix&> H2 = boost::none) const {
|
||||||
|
const size_t p = X::Dim();
|
||||||
|
if (H1) *H1 = -eye(p);
|
||||||
|
if (H2) *H2 = eye(p);
|
||||||
|
return x1.localCoordinates(x2);
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
/** Serialization function */
|
||||||
|
friend class boost::serialization::access;
|
||||||
|
template<class ARCHIVE>
|
||||||
|
void serialize(ARCHIVE & ar, const unsigned int version) {
|
||||||
|
ar & boost::serialization::make_nvp("NonlinearFactor2",
|
||||||
|
boost::serialization::base_object<Base>(*this));
|
||||||
|
}
|
||||||
|
}; // \NonlinearEquality2
|
||||||
|
|
||||||
} // namespace gtsam
|
} // namespace gtsam
|
||||||
|
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <gtsam/base/Lie.h>
|
#include <gtsam/base/Lie.h>
|
||||||
#include <gtsam/nonlinear/NonlinearConstraint.h>
|
#include <gtsam/nonlinear/NonlinearFactor.h>
|
||||||
|
|
||||||
namespace gtsam {
|
namespace gtsam {
|
||||||
|
|
||||||
|
|
|
@ -21,7 +21,7 @@
|
||||||
|
|
||||||
#include <gtsam/base/numericalDerivative.h>
|
#include <gtsam/base/numericalDerivative.h>
|
||||||
|
|
||||||
#include <gtsam/nonlinear/NonlinearConstraint.h>
|
#include <gtsam/nonlinear/NonlinearEquality.h>
|
||||||
#include <gtsam/slam/BetweenFactor.h>
|
#include <gtsam/slam/BetweenFactor.h>
|
||||||
#include <gtsam/slam/BoundingConstraint.h>
|
#include <gtsam/slam/BoundingConstraint.h>
|
||||||
#include <gtsam/slam/simulated2D.h>
|
#include <gtsam/slam/simulated2D.h>
|
||||||
|
|
|
@ -19,7 +19,6 @@ check_PROGRAMS += testSymbolicBayesNet testSymbolicFactorGraph
|
||||||
check_PROGRAMS += testTupleValues
|
check_PROGRAMS += testTupleValues
|
||||||
check_PROGRAMS += testNonlinearISAM
|
check_PROGRAMS += testNonlinearISAM
|
||||||
check_PROGRAMS += testBoundingConstraint
|
check_PROGRAMS += testBoundingConstraint
|
||||||
check_PROGRAMS += testNonlinearEqualityConstraint
|
|
||||||
check_PROGRAMS += testPose2SLAMwSPCG
|
check_PROGRAMS += testPose2SLAMwSPCG
|
||||||
check_PROGRAMS += testGaussianISAM2
|
check_PROGRAMS += testGaussianISAM2
|
||||||
check_PROGRAMS += testExtendedKalmanFilter
|
check_PROGRAMS += testExtendedKalmanFilter
|
||||||
|
|
|
@ -18,6 +18,8 @@
|
||||||
|
|
||||||
#include <gtsam/geometry/Pose2.h>
|
#include <gtsam/geometry/Pose2.h>
|
||||||
#include <gtsam/slam/PriorFactor.h>
|
#include <gtsam/slam/PriorFactor.h>
|
||||||
|
#include <gtsam/slam/simulated2DConstraints.h>
|
||||||
|
#include <gtsam/slam/visualSLAM.h>
|
||||||
#include <gtsam/nonlinear/NonlinearEquality.h>
|
#include <gtsam/nonlinear/NonlinearEquality.h>
|
||||||
#include <gtsam/nonlinear/NonlinearFactorGraph.h>
|
#include <gtsam/nonlinear/NonlinearFactorGraph.h>
|
||||||
#include <gtsam/nonlinear/NonlinearOptimizer-inl.h>
|
#include <gtsam/nonlinear/NonlinearOptimizer-inl.h>
|
||||||
|
@ -27,6 +29,10 @@
|
||||||
using namespace std;
|
using namespace std;
|
||||||
using namespace gtsam;
|
using namespace gtsam;
|
||||||
|
|
||||||
|
namespace eq2D = gtsam::simulated2D::equality_constraints;
|
||||||
|
|
||||||
|
static const double tol = 1e-5;
|
||||||
|
|
||||||
typedef TypedSymbol<Pose2, 'x'> PoseKey;
|
typedef TypedSymbol<Pose2, 'x'> PoseKey;
|
||||||
typedef Values<PoseKey> PoseValues;
|
typedef Values<PoseKey> PoseValues;
|
||||||
typedef PriorFactor<PoseValues, PoseKey> PosePrior;
|
typedef PriorFactor<PoseValues, PoseKey> PosePrior;
|
||||||
|
@ -243,6 +249,346 @@ TEST ( NonlinearEquality, allow_error_optimize_with_factors ) {
|
||||||
EXPECT(assert_equal(expected, *result.values()));
|
EXPECT(assert_equal(expected, *result.values()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
SharedDiagonal hard_model = noiseModel::Constrained::All(2);
|
||||||
|
SharedDiagonal soft_model = noiseModel::Isotropic::Sigma(2, 1.0);
|
||||||
|
|
||||||
|
typedef NonlinearFactorGraph<simulated2D::Values> Graph;
|
||||||
|
typedef boost::shared_ptr<Graph> shared_graph;
|
||||||
|
typedef boost::shared_ptr<simulated2D::Values> shared_values;
|
||||||
|
typedef NonlinearOptimizer<Graph, simulated2D::Values> Optimizer;
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
TEST( testNonlinearEqualityConstraint, unary_basics ) {
|
||||||
|
Point2 pt(1.0, 2.0);
|
||||||
|
simulated2D::PoseKey key(1);
|
||||||
|
double mu = 1000.0;
|
||||||
|
eq2D::UnaryEqualityConstraint constraint(pt, key, mu);
|
||||||
|
|
||||||
|
simulated2D::Values config1;
|
||||||
|
config1.insert(key, pt);
|
||||||
|
EXPECT(constraint.active(config1));
|
||||||
|
EXPECT(assert_equal(zero(2), constraint.evaluateError(pt), tol));
|
||||||
|
EXPECT(assert_equal(zero(2), constraint.unwhitenedError(config1), tol));
|
||||||
|
EXPECT_DOUBLES_EQUAL(0.0, constraint.error(config1), tol);
|
||||||
|
|
||||||
|
simulated2D::Values config2;
|
||||||
|
Point2 ptBad1(2.0, 2.0);
|
||||||
|
config2.insert(key, ptBad1);
|
||||||
|
EXPECT(constraint.active(config2));
|
||||||
|
EXPECT(assert_equal(Vector_(2, 1.0, 0.0), constraint.evaluateError(ptBad1), tol));
|
||||||
|
EXPECT(assert_equal(Vector_(2, 1.0, 0.0), constraint.unwhitenedError(config2), tol));
|
||||||
|
EXPECT_DOUBLES_EQUAL(500.0, constraint.error(config2), tol);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
TEST( testNonlinearEqualityConstraint, unary_linearization ) {
|
||||||
|
Point2 pt(1.0, 2.0);
|
||||||
|
simulated2D::PoseKey key(1);
|
||||||
|
double mu = 1000.0;
|
||||||
|
Ordering ordering;
|
||||||
|
ordering += key;
|
||||||
|
eq2D::UnaryEqualityConstraint constraint(pt, key, mu);
|
||||||
|
|
||||||
|
simulated2D::Values config1;
|
||||||
|
config1.insert(key, pt);
|
||||||
|
GaussianFactor::shared_ptr actual1 = constraint.linearize(config1, ordering);
|
||||||
|
GaussianFactor::shared_ptr expected1(new JacobianFactor(ordering[key], eye(2,2), zero(2), hard_model));
|
||||||
|
EXPECT(assert_equal(*expected1, *actual1, tol));
|
||||||
|
|
||||||
|
simulated2D::Values config2;
|
||||||
|
Point2 ptBad(2.0, 2.0);
|
||||||
|
config2.insert(key, ptBad);
|
||||||
|
GaussianFactor::shared_ptr actual2 = constraint.linearize(config2, ordering);
|
||||||
|
GaussianFactor::shared_ptr expected2(new JacobianFactor(ordering[key], eye(2,2), Vector_(2,-1.0,0.0), hard_model));
|
||||||
|
EXPECT(assert_equal(*expected2, *actual2, tol));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
TEST( testNonlinearEqualityConstraint, unary_simple_optimization ) {
|
||||||
|
// create a single-node graph with a soft and hard constraint to
|
||||||
|
// ensure that the hard constraint overrides the soft constraint
|
||||||
|
Point2 truth_pt(1.0, 2.0);
|
||||||
|
simulated2D::PoseKey key(1);
|
||||||
|
double mu = 10.0;
|
||||||
|
eq2D::UnaryEqualityConstraint::shared_ptr constraint(
|
||||||
|
new eq2D::UnaryEqualityConstraint(truth_pt, key, mu));
|
||||||
|
|
||||||
|
Point2 badPt(100.0, -200.0);
|
||||||
|
simulated2D::Prior::shared_ptr factor(
|
||||||
|
new simulated2D::Prior(badPt, soft_model, key));
|
||||||
|
|
||||||
|
shared_graph graph(new Graph());
|
||||||
|
graph->push_back(constraint);
|
||||||
|
graph->push_back(factor);
|
||||||
|
|
||||||
|
shared_values initValues(new simulated2D::Values());
|
||||||
|
initValues->insert(key, badPt);
|
||||||
|
|
||||||
|
// verify error values
|
||||||
|
EXPECT(constraint->active(*initValues));
|
||||||
|
|
||||||
|
simulated2D::Values expected;
|
||||||
|
expected.insert(key, truth_pt);
|
||||||
|
EXPECT(constraint->active(expected));
|
||||||
|
EXPECT_DOUBLES_EQUAL(0.0, constraint->error(expected), tol);
|
||||||
|
|
||||||
|
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initValues);
|
||||||
|
EXPECT(assert_equal(expected, *actual, tol));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
TEST( testNonlinearEqualityConstraint, odo_basics ) {
|
||||||
|
Point2 x1(1.0, 2.0), x2(2.0, 3.0), odom(1.0, 1.0);
|
||||||
|
simulated2D::PoseKey key1(1), key2(2);
|
||||||
|
double mu = 1000.0;
|
||||||
|
eq2D::OdoEqualityConstraint constraint(odom, key1, key2, mu);
|
||||||
|
|
||||||
|
simulated2D::Values config1;
|
||||||
|
config1.insert(key1, x1);
|
||||||
|
config1.insert(key2, x2);
|
||||||
|
EXPECT(constraint.active(config1));
|
||||||
|
EXPECT(assert_equal(zero(2), constraint.evaluateError(x1, x2), tol));
|
||||||
|
EXPECT(assert_equal(zero(2), constraint.unwhitenedError(config1), tol));
|
||||||
|
EXPECT_DOUBLES_EQUAL(0.0, constraint.error(config1), tol);
|
||||||
|
|
||||||
|
simulated2D::Values config2;
|
||||||
|
Point2 x1bad(2.0, 2.0);
|
||||||
|
Point2 x2bad(2.0, 2.0);
|
||||||
|
config2.insert(key1, x1bad);
|
||||||
|
config2.insert(key2, x2bad);
|
||||||
|
EXPECT(constraint.active(config2));
|
||||||
|
EXPECT(assert_equal(Vector_(2, -1.0, -1.0), constraint.evaluateError(x1bad, x2bad), tol));
|
||||||
|
EXPECT(assert_equal(Vector_(2, -1.0, -1.0), constraint.unwhitenedError(config2), tol));
|
||||||
|
EXPECT_DOUBLES_EQUAL(1000.0, constraint.error(config2), tol);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
TEST( testNonlinearEqualityConstraint, odo_linearization ) {
|
||||||
|
Point2 x1(1.0, 2.0), x2(2.0, 3.0), odom(1.0, 1.0);
|
||||||
|
simulated2D::PoseKey key1(1), key2(2);
|
||||||
|
double mu = 1000.0;
|
||||||
|
Ordering ordering;
|
||||||
|
ordering += key1, key2;
|
||||||
|
eq2D::OdoEqualityConstraint constraint(odom, key1, key2, mu);
|
||||||
|
|
||||||
|
simulated2D::Values config1;
|
||||||
|
config1.insert(key1, x1);
|
||||||
|
config1.insert(key2, x2);
|
||||||
|
GaussianFactor::shared_ptr actual1 = constraint.linearize(config1, ordering);
|
||||||
|
GaussianFactor::shared_ptr expected1(
|
||||||
|
new JacobianFactor(ordering[key1], -eye(2,2), ordering[key2],
|
||||||
|
eye(2,2), zero(2), hard_model));
|
||||||
|
EXPECT(assert_equal(*expected1, *actual1, tol));
|
||||||
|
|
||||||
|
simulated2D::Values config2;
|
||||||
|
Point2 x1bad(2.0, 2.0);
|
||||||
|
Point2 x2bad(2.0, 2.0);
|
||||||
|
config2.insert(key1, x1bad);
|
||||||
|
config2.insert(key2, x2bad);
|
||||||
|
GaussianFactor::shared_ptr actual2 = constraint.linearize(config2, ordering);
|
||||||
|
GaussianFactor::shared_ptr expected2(
|
||||||
|
new JacobianFactor(ordering[key1], -eye(2,2), ordering[key2],
|
||||||
|
eye(2,2), Vector_(2, 1.0, 1.0), hard_model));
|
||||||
|
EXPECT(assert_equal(*expected2, *actual2, tol));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ************************************************************************* */
|
||||||
|
TEST( testNonlinearEqualityConstraint, odo_simple_optimize ) {
|
||||||
|
// create a two-node graph, connected by an odometry constraint, with
|
||||||
|
// a hard prior on one variable, and a conflicting soft prior
|
||||||
|
// on the other variable - the constraints should override the soft constraint
|
||||||
|
Point2 truth_pt1(1.0, 2.0), truth_pt2(3.0, 2.0);
|
||||||
|
simulated2D::PoseKey key1(1), key2(2);
|
||||||
|
|
||||||
|
// hard prior on x1
|
||||||
|
eq2D::UnaryEqualityConstraint::shared_ptr constraint1(
|
||||||
|
new eq2D::UnaryEqualityConstraint(truth_pt1, key1));
|
||||||
|
|
||||||
|
// soft prior on x2
|
||||||
|
Point2 badPt(100.0, -200.0);
|
||||||
|
simulated2D::Prior::shared_ptr factor(
|
||||||
|
new simulated2D::Prior(badPt, soft_model, key2));
|
||||||
|
|
||||||
|
// odometry constraint
|
||||||
|
eq2D::OdoEqualityConstraint::shared_ptr constraint2(
|
||||||
|
new eq2D::OdoEqualityConstraint(
|
||||||
|
truth_pt1.between(truth_pt2), key1, key2));
|
||||||
|
|
||||||
|
shared_graph graph(new Graph());
|
||||||
|
graph->push_back(constraint1);
|
||||||
|
graph->push_back(constraint2);
|
||||||
|
graph->push_back(factor);
|
||||||
|
|
||||||
|
shared_values initValues(new simulated2D::Values());
|
||||||
|
initValues->insert(key1, Point2());
|
||||||
|
initValues->insert(key2, badPt);
|
||||||
|
|
||||||
|
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initValues);
|
||||||
|
simulated2D::Values expected;
|
||||||
|
expected.insert(key1, truth_pt1);
|
||||||
|
expected.insert(key2, truth_pt2);
|
||||||
|
CHECK(assert_equal(expected, *actual, tol));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ********************************************************************* */
|
||||||
|
TEST (testNonlinearEqualityConstraint, two_pose ) {
|
||||||
|
/*
|
||||||
|
* Determining a ground truth linear system
|
||||||
|
* with two poses seeing one landmark, with each pose
|
||||||
|
* constrained to a particular value
|
||||||
|
*/
|
||||||
|
|
||||||
|
shared_graph graph(new Graph());
|
||||||
|
|
||||||
|
simulated2D::PoseKey x1(1), x2(2);
|
||||||
|
simulated2D::PointKey l1(1), l2(2);
|
||||||
|
Point2 pt_x1(1.0, 1.0),
|
||||||
|
pt_x2(5.0, 6.0);
|
||||||
|
graph->add(eq2D::UnaryEqualityConstraint(pt_x1, x1));
|
||||||
|
graph->add(eq2D::UnaryEqualityConstraint(pt_x2, x2));
|
||||||
|
|
||||||
|
Point2 z1(0.0, 5.0);
|
||||||
|
SharedNoiseModel sigma(noiseModel::Isotropic::Sigma(2, 0.1));
|
||||||
|
graph->add(simulated2D::Measurement(z1, sigma, x1,l1));
|
||||||
|
|
||||||
|
Point2 z2(-4.0, 0.0);
|
||||||
|
graph->add(simulated2D::Measurement(z2, sigma, x2,l2));
|
||||||
|
|
||||||
|
graph->add(eq2D::PointEqualityConstraint(l1, l2));
|
||||||
|
|
||||||
|
shared_values initialEstimate(new simulated2D::Values());
|
||||||
|
initialEstimate->insert(x1, pt_x1);
|
||||||
|
initialEstimate->insert(x2, Point2());
|
||||||
|
initialEstimate->insert(l1, Point2(1.0, 6.0)); // ground truth
|
||||||
|
initialEstimate->insert(l2, Point2(-4.0, 0.0)); // starting with a separate reference frame
|
||||||
|
|
||||||
|
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initialEstimate);
|
||||||
|
|
||||||
|
simulated2D::Values expected;
|
||||||
|
expected.insert(x1, pt_x1);
|
||||||
|
expected.insert(l1, Point2(1.0, 6.0));
|
||||||
|
expected.insert(l2, Point2(1.0, 6.0));
|
||||||
|
expected.insert(x2, Point2(5.0, 6.0));
|
||||||
|
CHECK(assert_equal(expected, *actual, 1e-5));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ********************************************************************* */
|
||||||
|
TEST (testNonlinearEqualityConstraint, map_warp ) {
|
||||||
|
// get a graph
|
||||||
|
shared_graph graph(new Graph());
|
||||||
|
|
||||||
|
// keys
|
||||||
|
simulated2D::PoseKey x1(1), x2(2);
|
||||||
|
simulated2D::PointKey l1(1), l2(2);
|
||||||
|
|
||||||
|
// constant constraint on x1
|
||||||
|
Point2 pose1(1.0, 1.0);
|
||||||
|
graph->add(eq2D::UnaryEqualityConstraint(pose1, x1));
|
||||||
|
|
||||||
|
SharedDiagonal sigma = noiseModel::Isotropic::Sigma(1,0.1);
|
||||||
|
|
||||||
|
// measurement from x1 to l1
|
||||||
|
Point2 z1(0.0, 5.0);
|
||||||
|
graph->add(simulated2D::Measurement(z1, sigma, x1, l1));
|
||||||
|
|
||||||
|
// measurement from x2 to l2
|
||||||
|
Point2 z2(-4.0, 0.0);
|
||||||
|
graph->add(simulated2D::Measurement(z2, sigma, x2, l2));
|
||||||
|
|
||||||
|
// equality constraint between l1 and l2
|
||||||
|
graph->add(eq2D::PointEqualityConstraint(l1, l2));
|
||||||
|
|
||||||
|
// create an initial estimate
|
||||||
|
shared_values initialEstimate(new simulated2D::Values());
|
||||||
|
initialEstimate->insert(x1, Point2( 1.0, 1.0));
|
||||||
|
initialEstimate->insert(l1, Point2( 1.0, 6.0));
|
||||||
|
initialEstimate->insert(l2, Point2(-4.0, 0.0)); // starting with a separate reference frame
|
||||||
|
initialEstimate->insert(x2, Point2( 0.0, 0.0)); // other pose starts at origin
|
||||||
|
|
||||||
|
// optimize
|
||||||
|
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initialEstimate);
|
||||||
|
|
||||||
|
simulated2D::Values expected;
|
||||||
|
expected.insert(x1, Point2(1.0, 1.0));
|
||||||
|
expected.insert(l1, Point2(1.0, 6.0));
|
||||||
|
expected.insert(l2, Point2(1.0, 6.0));
|
||||||
|
expected.insert(x2, Point2(5.0, 6.0));
|
||||||
|
CHECK(assert_equal(expected, *actual, tol));
|
||||||
|
}
|
||||||
|
|
||||||
|
// make a realistic calibration matrix
|
||||||
|
double fov = 60; // degrees
|
||||||
|
size_t w=640,h=480;
|
||||||
|
Cal3_S2 K(fov,w,h);
|
||||||
|
boost::shared_ptr<Cal3_S2> shK(new Cal3_S2(K));
|
||||||
|
|
||||||
|
// typedefs for visual SLAM example
|
||||||
|
typedef visualSLAM::Values VValues;
|
||||||
|
typedef boost::shared_ptr<VValues> shared_vconfig;
|
||||||
|
typedef visualSLAM::Graph VGraph;
|
||||||
|
typedef NonlinearOptimizer<VGraph,VValues> VOptimizer;
|
||||||
|
|
||||||
|
// factors for visual slam
|
||||||
|
typedef NonlinearEquality2<VValues, visualSLAM::PointKey> Point3Equality;
|
||||||
|
|
||||||
|
/* ********************************************************************* */
|
||||||
|
TEST (testNonlinearEqualityConstraint, stereo_constrained ) {
|
||||||
|
|
||||||
|
// create initial estimates
|
||||||
|
Rot3 faceDownY(Matrix_(3,3,
|
||||||
|
1.0, 0.0, 0.0,
|
||||||
|
0.0, 0.0, 1.0,
|
||||||
|
0.0, -1.0, 0.0));
|
||||||
|
Pose3 pose1(faceDownY, Point3()); // origin, left camera
|
||||||
|
SimpleCamera camera1(K, pose1);
|
||||||
|
Pose3 pose2(faceDownY, Point3(2.0, 0.0, 0.0)); // 2 units to the left
|
||||||
|
SimpleCamera camera2(K, pose2);
|
||||||
|
Point3 landmark(1.0, 5.0, 0.0); //centered between the cameras, 5 units away
|
||||||
|
|
||||||
|
// keys
|
||||||
|
visualSLAM::PoseKey x1(1), x2(2);
|
||||||
|
visualSLAM::PointKey l1(1), l2(2);
|
||||||
|
|
||||||
|
// create graph
|
||||||
|
VGraph::shared_graph graph(new VGraph());
|
||||||
|
|
||||||
|
// create equality constraints for poses
|
||||||
|
graph->addPoseConstraint(1, camera1.pose());
|
||||||
|
graph->addPoseConstraint(2, camera2.pose());
|
||||||
|
|
||||||
|
// create factors
|
||||||
|
SharedDiagonal vmodel = noiseModel::Unit::Create(3);
|
||||||
|
graph->addMeasurement(camera1.project(landmark), vmodel, 1, 1, shK);
|
||||||
|
graph->addMeasurement(camera2.project(landmark), vmodel, 2, 2, shK);
|
||||||
|
|
||||||
|
// add equality constraint
|
||||||
|
graph->add(Point3Equality(l1, l2));
|
||||||
|
|
||||||
|
// create initial data
|
||||||
|
Point3 landmark1(0.5, 5.0, 0.0);
|
||||||
|
Point3 landmark2(1.5, 5.0, 0.0);
|
||||||
|
|
||||||
|
shared_vconfig initValues(new VValues());
|
||||||
|
initValues->insert(x1, pose1);
|
||||||
|
initValues->insert(x2, pose2);
|
||||||
|
initValues->insert(l1, landmark1);
|
||||||
|
initValues->insert(l2, landmark2);
|
||||||
|
|
||||||
|
// optimize
|
||||||
|
VOptimizer::shared_values actual = VOptimizer::optimizeLM(graph, initValues);
|
||||||
|
|
||||||
|
// create config
|
||||||
|
VValues truthValues;
|
||||||
|
truthValues.insert(x1, camera1.pose());
|
||||||
|
truthValues.insert(x2, camera2.pose());
|
||||||
|
truthValues.insert(l1, landmark);
|
||||||
|
truthValues.insert(l2, landmark);
|
||||||
|
|
||||||
|
// check if correct
|
||||||
|
CHECK(assert_equal(truthValues, *actual, 1e-5));
|
||||||
|
}
|
||||||
|
|
||||||
/* ************************************************************************* */
|
/* ************************************************************************* */
|
||||||
int main() { TestResult tr; return TestRegistry::runAllTests(tr); }
|
int main() { TestResult tr; return TestRegistry::runAllTests(tr); }
|
||||||
/* ************************************************************************* */
|
/* ************************************************************************* */
|
||||||
|
|
|
@ -1,375 +0,0 @@
|
||||||
/* ----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
* GTSAM Copyright 2010, Georgia Tech Research Corporation,
|
|
||||||
* Atlanta, Georgia 30332-0415
|
|
||||||
* All Rights Reserved
|
|
||||||
* Authors: Frank Dellaert, et al. (see THANKS for the full author list)
|
|
||||||
|
|
||||||
* See LICENSE for the license information
|
|
||||||
|
|
||||||
* -------------------------------------------------------------------------- */
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @file testNonlinearEqualityConstraint.cpp
|
|
||||||
* @author Alex Cunningham
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include <CppUnitLite/TestHarness.h>
|
|
||||||
|
|
||||||
#include <gtsam/slam/simulated2DConstraints.h>
|
|
||||||
#include <gtsam/slam/visualSLAM.h>
|
|
||||||
#include <gtsam/nonlinear/NonlinearFactorGraph-inl.h>
|
|
||||||
#include <gtsam/nonlinear/NonlinearOptimizer-inl.h>
|
|
||||||
|
|
||||||
namespace eq2D = gtsam::simulated2D::equality_constraints;
|
|
||||||
|
|
||||||
using namespace std;
|
|
||||||
using namespace gtsam;
|
|
||||||
|
|
||||||
static const double tol = 1e-5;
|
|
||||||
|
|
||||||
SharedDiagonal hard_model = noiseModel::Constrained::All(2);
|
|
||||||
SharedDiagonal soft_model = noiseModel::Isotropic::Sigma(2, 1.0);
|
|
||||||
|
|
||||||
typedef NonlinearFactorGraph<simulated2D::Values> Graph;
|
|
||||||
typedef boost::shared_ptr<Graph> shared_graph;
|
|
||||||
typedef boost::shared_ptr<simulated2D::Values> shared_values;
|
|
||||||
typedef NonlinearOptimizer<Graph, simulated2D::Values> Optimizer;
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
TEST( testNonlinearEqualityConstraint, unary_basics ) {
|
|
||||||
Point2 pt(1.0, 2.0);
|
|
||||||
simulated2D::PoseKey key(1);
|
|
||||||
double mu = 1000.0;
|
|
||||||
eq2D::UnaryEqualityConstraint constraint(pt, key, mu);
|
|
||||||
|
|
||||||
simulated2D::Values config1;
|
|
||||||
config1.insert(key, pt);
|
|
||||||
EXPECT(constraint.active(config1));
|
|
||||||
EXPECT(assert_equal(zero(2), constraint.evaluateError(pt), tol));
|
|
||||||
EXPECT(assert_equal(zero(2), constraint.unwhitenedError(config1), tol));
|
|
||||||
EXPECT_DOUBLES_EQUAL(0.0, constraint.error(config1), tol);
|
|
||||||
|
|
||||||
simulated2D::Values config2;
|
|
||||||
Point2 ptBad1(2.0, 2.0);
|
|
||||||
config2.insert(key, ptBad1);
|
|
||||||
EXPECT(constraint.active(config2));
|
|
||||||
EXPECT(assert_equal(Vector_(2, 1.0, 0.0), constraint.evaluateError(ptBad1), tol));
|
|
||||||
EXPECT(assert_equal(Vector_(2, 1.0, 0.0), constraint.unwhitenedError(config2), tol));
|
|
||||||
EXPECT_DOUBLES_EQUAL(500.0, constraint.error(config2), tol);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
TEST( testNonlinearEqualityConstraint, unary_linearization ) {
|
|
||||||
Point2 pt(1.0, 2.0);
|
|
||||||
simulated2D::PoseKey key(1);
|
|
||||||
double mu = 1000.0;
|
|
||||||
Ordering ordering;
|
|
||||||
ordering += key;
|
|
||||||
eq2D::UnaryEqualityConstraint constraint(pt, key, mu);
|
|
||||||
|
|
||||||
simulated2D::Values config1;
|
|
||||||
config1.insert(key, pt);
|
|
||||||
GaussianFactor::shared_ptr actual1 = constraint.linearize(config1, ordering);
|
|
||||||
GaussianFactor::shared_ptr expected1(new JacobianFactor(ordering[key], eye(2,2), zero(2), hard_model));
|
|
||||||
EXPECT(assert_equal(*expected1, *actual1, tol));
|
|
||||||
|
|
||||||
simulated2D::Values config2;
|
|
||||||
Point2 ptBad(2.0, 2.0);
|
|
||||||
config2.insert(key, ptBad);
|
|
||||||
GaussianFactor::shared_ptr actual2 = constraint.linearize(config2, ordering);
|
|
||||||
GaussianFactor::shared_ptr expected2(new JacobianFactor(ordering[key], eye(2,2), Vector_(2,-1.0,0.0), hard_model));
|
|
||||||
EXPECT(assert_equal(*expected2, *actual2, tol));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
TEST( testNonlinearEqualityConstraint, unary_simple_optimization ) {
|
|
||||||
// create a single-node graph with a soft and hard constraint to
|
|
||||||
// ensure that the hard constraint overrides the soft constraint
|
|
||||||
Point2 truth_pt(1.0, 2.0);
|
|
||||||
simulated2D::PoseKey key(1);
|
|
||||||
double mu = 10.0;
|
|
||||||
eq2D::UnaryEqualityConstraint::shared_ptr constraint(
|
|
||||||
new eq2D::UnaryEqualityConstraint(truth_pt, key, mu));
|
|
||||||
|
|
||||||
Point2 badPt(100.0, -200.0);
|
|
||||||
simulated2D::Prior::shared_ptr factor(
|
|
||||||
new simulated2D::Prior(badPt, soft_model, key));
|
|
||||||
|
|
||||||
shared_graph graph(new Graph());
|
|
||||||
graph->push_back(constraint);
|
|
||||||
graph->push_back(factor);
|
|
||||||
|
|
||||||
shared_values initValues(new simulated2D::Values());
|
|
||||||
initValues->insert(key, badPt);
|
|
||||||
|
|
||||||
// verify error values
|
|
||||||
EXPECT(constraint->active(*initValues));
|
|
||||||
|
|
||||||
simulated2D::Values expected;
|
|
||||||
expected.insert(key, truth_pt);
|
|
||||||
EXPECT(constraint->active(expected));
|
|
||||||
EXPECT_DOUBLES_EQUAL(0.0, constraint->error(expected), tol);
|
|
||||||
|
|
||||||
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initValues);
|
|
||||||
EXPECT(assert_equal(expected, *actual, tol));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
TEST( testNonlinearEqualityConstraint, odo_basics ) {
|
|
||||||
Point2 x1(1.0, 2.0), x2(2.0, 3.0), odom(1.0, 1.0);
|
|
||||||
simulated2D::PoseKey key1(1), key2(2);
|
|
||||||
double mu = 1000.0;
|
|
||||||
eq2D::OdoEqualityConstraint constraint(odom, key1, key2, mu);
|
|
||||||
|
|
||||||
simulated2D::Values config1;
|
|
||||||
config1.insert(key1, x1);
|
|
||||||
config1.insert(key2, x2);
|
|
||||||
EXPECT(constraint.active(config1));
|
|
||||||
EXPECT(assert_equal(zero(2), constraint.evaluateError(x1, x2), tol));
|
|
||||||
EXPECT(assert_equal(zero(2), constraint.unwhitenedError(config1), tol));
|
|
||||||
EXPECT_DOUBLES_EQUAL(0.0, constraint.error(config1), tol);
|
|
||||||
|
|
||||||
simulated2D::Values config2;
|
|
||||||
Point2 x1bad(2.0, 2.0);
|
|
||||||
Point2 x2bad(2.0, 2.0);
|
|
||||||
config2.insert(key1, x1bad);
|
|
||||||
config2.insert(key2, x2bad);
|
|
||||||
EXPECT(constraint.active(config2));
|
|
||||||
EXPECT(assert_equal(Vector_(2, -1.0, -1.0), constraint.evaluateError(x1bad, x2bad), tol));
|
|
||||||
EXPECT(assert_equal(Vector_(2, -1.0, -1.0), constraint.unwhitenedError(config2), tol));
|
|
||||||
EXPECT_DOUBLES_EQUAL(1000.0, constraint.error(config2), tol);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
TEST( testNonlinearEqualityConstraint, odo_linearization ) {
|
|
||||||
Point2 x1(1.0, 2.0), x2(2.0, 3.0), odom(1.0, 1.0);
|
|
||||||
simulated2D::PoseKey key1(1), key2(2);
|
|
||||||
double mu = 1000.0;
|
|
||||||
Ordering ordering;
|
|
||||||
ordering += key1, key2;
|
|
||||||
eq2D::OdoEqualityConstraint constraint(odom, key1, key2, mu);
|
|
||||||
|
|
||||||
simulated2D::Values config1;
|
|
||||||
config1.insert(key1, x1);
|
|
||||||
config1.insert(key2, x2);
|
|
||||||
GaussianFactor::shared_ptr actual1 = constraint.linearize(config1, ordering);
|
|
||||||
GaussianFactor::shared_ptr expected1(
|
|
||||||
new JacobianFactor(ordering[key1], -eye(2,2), ordering[key2],
|
|
||||||
eye(2,2), zero(2), hard_model));
|
|
||||||
EXPECT(assert_equal(*expected1, *actual1, tol));
|
|
||||||
|
|
||||||
simulated2D::Values config2;
|
|
||||||
Point2 x1bad(2.0, 2.0);
|
|
||||||
Point2 x2bad(2.0, 2.0);
|
|
||||||
config2.insert(key1, x1bad);
|
|
||||||
config2.insert(key2, x2bad);
|
|
||||||
GaussianFactor::shared_ptr actual2 = constraint.linearize(config2, ordering);
|
|
||||||
GaussianFactor::shared_ptr expected2(
|
|
||||||
new JacobianFactor(ordering[key1], -eye(2,2), ordering[key2],
|
|
||||||
eye(2,2), Vector_(2, 1.0, 1.0), hard_model));
|
|
||||||
EXPECT(assert_equal(*expected2, *actual2, tol));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
TEST( testNonlinearEqualityConstraint, odo_simple_optimize ) {
|
|
||||||
// create a two-node graph, connected by an odometry constraint, with
|
|
||||||
// a hard prior on one variable, and a conflicting soft prior
|
|
||||||
// on the other variable - the constraints should override the soft constraint
|
|
||||||
Point2 truth_pt1(1.0, 2.0), truth_pt2(3.0, 2.0);
|
|
||||||
simulated2D::PoseKey key1(1), key2(2);
|
|
||||||
|
|
||||||
// hard prior on x1
|
|
||||||
eq2D::UnaryEqualityConstraint::shared_ptr constraint1(
|
|
||||||
new eq2D::UnaryEqualityConstraint(truth_pt1, key1));
|
|
||||||
|
|
||||||
// soft prior on x2
|
|
||||||
Point2 badPt(100.0, -200.0);
|
|
||||||
simulated2D::Prior::shared_ptr factor(
|
|
||||||
new simulated2D::Prior(badPt, soft_model, key2));
|
|
||||||
|
|
||||||
// odometry constraint
|
|
||||||
eq2D::OdoEqualityConstraint::shared_ptr constraint2(
|
|
||||||
new eq2D::OdoEqualityConstraint(
|
|
||||||
truth_pt1.between(truth_pt2), key1, key2));
|
|
||||||
|
|
||||||
shared_graph graph(new Graph());
|
|
||||||
graph->push_back(constraint1);
|
|
||||||
graph->push_back(constraint2);
|
|
||||||
graph->push_back(factor);
|
|
||||||
|
|
||||||
shared_values initValues(new simulated2D::Values());
|
|
||||||
initValues->insert(key1, Point2());
|
|
||||||
initValues->insert(key2, badPt);
|
|
||||||
|
|
||||||
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initValues);
|
|
||||||
simulated2D::Values expected;
|
|
||||||
expected.insert(key1, truth_pt1);
|
|
||||||
expected.insert(key2, truth_pt2);
|
|
||||||
CHECK(assert_equal(expected, *actual, tol));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ********************************************************************* */
|
|
||||||
TEST (testNonlinearEqualityConstraint, two_pose ) {
|
|
||||||
/*
|
|
||||||
* Determining a ground truth linear system
|
|
||||||
* with two poses seeing one landmark, with each pose
|
|
||||||
* constrained to a particular value
|
|
||||||
*/
|
|
||||||
|
|
||||||
shared_graph graph(new Graph());
|
|
||||||
|
|
||||||
simulated2D::PoseKey x1(1), x2(2);
|
|
||||||
simulated2D::PointKey l1(1), l2(2);
|
|
||||||
Point2 pt_x1(1.0, 1.0),
|
|
||||||
pt_x2(5.0, 6.0);
|
|
||||||
graph->add(eq2D::UnaryEqualityConstraint(pt_x1, x1));
|
|
||||||
graph->add(eq2D::UnaryEqualityConstraint(pt_x2, x2));
|
|
||||||
|
|
||||||
Point2 z1(0.0, 5.0);
|
|
||||||
SharedNoiseModel sigma(noiseModel::Isotropic::Sigma(2, 0.1));
|
|
||||||
graph->add(simulated2D::Measurement(z1, sigma, x1,l1));
|
|
||||||
|
|
||||||
Point2 z2(-4.0, 0.0);
|
|
||||||
graph->add(simulated2D::Measurement(z2, sigma, x2,l2));
|
|
||||||
|
|
||||||
graph->add(eq2D::PointEqualityConstraint(l1, l2));
|
|
||||||
|
|
||||||
shared_values initialEstimate(new simulated2D::Values());
|
|
||||||
initialEstimate->insert(x1, pt_x1);
|
|
||||||
initialEstimate->insert(x2, Point2());
|
|
||||||
initialEstimate->insert(l1, Point2(1.0, 6.0)); // ground truth
|
|
||||||
initialEstimate->insert(l2, Point2(-4.0, 0.0)); // starting with a separate reference frame
|
|
||||||
|
|
||||||
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initialEstimate);
|
|
||||||
|
|
||||||
simulated2D::Values expected;
|
|
||||||
expected.insert(x1, pt_x1);
|
|
||||||
expected.insert(l1, Point2(1.0, 6.0));
|
|
||||||
expected.insert(l2, Point2(1.0, 6.0));
|
|
||||||
expected.insert(x2, Point2(5.0, 6.0));
|
|
||||||
CHECK(assert_equal(expected, *actual, 1e-5));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ********************************************************************* */
|
|
||||||
TEST (testNonlinearEqualityConstraint, map_warp ) {
|
|
||||||
// get a graph
|
|
||||||
shared_graph graph(new Graph());
|
|
||||||
|
|
||||||
// keys
|
|
||||||
simulated2D::PoseKey x1(1), x2(2);
|
|
||||||
simulated2D::PointKey l1(1), l2(2);
|
|
||||||
|
|
||||||
// constant constraint on x1
|
|
||||||
Point2 pose1(1.0, 1.0);
|
|
||||||
graph->add(eq2D::UnaryEqualityConstraint(pose1, x1));
|
|
||||||
|
|
||||||
SharedDiagonal sigma = noiseModel::Isotropic::Sigma(1,0.1);
|
|
||||||
|
|
||||||
// measurement from x1 to l1
|
|
||||||
Point2 z1(0.0, 5.0);
|
|
||||||
graph->add(simulated2D::Measurement(z1, sigma, x1, l1));
|
|
||||||
|
|
||||||
// measurement from x2 to l2
|
|
||||||
Point2 z2(-4.0, 0.0);
|
|
||||||
graph->add(simulated2D::Measurement(z2, sigma, x2, l2));
|
|
||||||
|
|
||||||
// equality constraint between l1 and l2
|
|
||||||
graph->add(eq2D::PointEqualityConstraint(l1, l2));
|
|
||||||
|
|
||||||
// create an initial estimate
|
|
||||||
shared_values initialEstimate(new simulated2D::Values());
|
|
||||||
initialEstimate->insert(x1, Point2( 1.0, 1.0));
|
|
||||||
initialEstimate->insert(l1, Point2( 1.0, 6.0));
|
|
||||||
initialEstimate->insert(l2, Point2(-4.0, 0.0)); // starting with a separate reference frame
|
|
||||||
initialEstimate->insert(x2, Point2( 0.0, 0.0)); // other pose starts at origin
|
|
||||||
|
|
||||||
// optimize
|
|
||||||
Optimizer::shared_values actual = Optimizer::optimizeLM(graph, initialEstimate);
|
|
||||||
|
|
||||||
simulated2D::Values expected;
|
|
||||||
expected.insert(x1, Point2(1.0, 1.0));
|
|
||||||
expected.insert(l1, Point2(1.0, 6.0));
|
|
||||||
expected.insert(l2, Point2(1.0, 6.0));
|
|
||||||
expected.insert(x2, Point2(5.0, 6.0));
|
|
||||||
CHECK(assert_equal(expected, *actual, tol));
|
|
||||||
}
|
|
||||||
|
|
||||||
// make a realistic calibration matrix
|
|
||||||
double fov = 60; // degrees
|
|
||||||
size_t w=640,h=480;
|
|
||||||
Cal3_S2 K(fov,w,h);
|
|
||||||
boost::shared_ptr<Cal3_S2> shK(new Cal3_S2(K));
|
|
||||||
|
|
||||||
// typedefs for visual SLAM example
|
|
||||||
typedef visualSLAM::Values VValues;
|
|
||||||
typedef boost::shared_ptr<VValues> shared_vconfig;
|
|
||||||
typedef visualSLAM::Graph VGraph;
|
|
||||||
typedef NonlinearOptimizer<VGraph,VValues> VOptimizer;
|
|
||||||
|
|
||||||
// factors for visual slam
|
|
||||||
typedef NonlinearEquality2<VValues, visualSLAM::PointKey> Point3Equality;
|
|
||||||
|
|
||||||
/* ********************************************************************* */
|
|
||||||
TEST (testNonlinearEqualityConstraint, stereo_constrained ) {
|
|
||||||
|
|
||||||
// create initial estimates
|
|
||||||
Rot3 faceDownY(Matrix_(3,3,
|
|
||||||
1.0, 0.0, 0.0,
|
|
||||||
0.0, 0.0, 1.0,
|
|
||||||
0.0, -1.0, 0.0));
|
|
||||||
Pose3 pose1(faceDownY, Point3()); // origin, left camera
|
|
||||||
SimpleCamera camera1(K, pose1);
|
|
||||||
Pose3 pose2(faceDownY, Point3(2.0, 0.0, 0.0)); // 2 units to the left
|
|
||||||
SimpleCamera camera2(K, pose2);
|
|
||||||
Point3 landmark(1.0, 5.0, 0.0); //centered between the cameras, 5 units away
|
|
||||||
|
|
||||||
// keys
|
|
||||||
visualSLAM::PoseKey x1(1), x2(2);
|
|
||||||
visualSLAM::PointKey l1(1), l2(2);
|
|
||||||
|
|
||||||
// create graph
|
|
||||||
VGraph::shared_graph graph(new VGraph());
|
|
||||||
|
|
||||||
// create equality constraints for poses
|
|
||||||
graph->addPoseConstraint(1, camera1.pose());
|
|
||||||
graph->addPoseConstraint(2, camera2.pose());
|
|
||||||
|
|
||||||
// create factors
|
|
||||||
SharedDiagonal vmodel = noiseModel::Unit::Create(3);
|
|
||||||
graph->addMeasurement(camera1.project(landmark), vmodel, 1, 1, shK);
|
|
||||||
graph->addMeasurement(camera2.project(landmark), vmodel, 2, 2, shK);
|
|
||||||
|
|
||||||
// add equality constraint
|
|
||||||
graph->add(Point3Equality(l1, l2));
|
|
||||||
|
|
||||||
// create initial data
|
|
||||||
Point3 landmark1(0.5, 5.0, 0.0);
|
|
||||||
Point3 landmark2(1.5, 5.0, 0.0);
|
|
||||||
|
|
||||||
shared_vconfig initValues(new VValues());
|
|
||||||
initValues->insert(x1, pose1);
|
|
||||||
initValues->insert(x2, pose2);
|
|
||||||
initValues->insert(l1, landmark1);
|
|
||||||
initValues->insert(l2, landmark2);
|
|
||||||
|
|
||||||
// optimize
|
|
||||||
VOptimizer::shared_values actual = VOptimizer::optimizeLM(graph, initValues);
|
|
||||||
|
|
||||||
// create config
|
|
||||||
VValues truthValues;
|
|
||||||
truthValues.insert(x1, camera1.pose());
|
|
||||||
truthValues.insert(x2, camera2.pose());
|
|
||||||
truthValues.insert(l1, landmark);
|
|
||||||
truthValues.insert(l2, landmark);
|
|
||||||
|
|
||||||
// check if correct
|
|
||||||
CHECK(assert_equal(truthValues, *actual, 1e-5));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* ************************************************************************* */
|
|
||||||
int main() { TestResult tr; return TestRegistry::runAllTests(tr); }
|
|
||||||
/* ************************************************************************* */
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue