Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Wrap NonlinearEquality2 #856

Merged
merged 3 commits into from
Aug 23, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
62 changes: 27 additions & 35 deletions gtsam/nonlinear/NonlinearEquality.h
Original file line number Diff line number Diff line change
Expand Up @@ -290,36 +290,30 @@ struct traits<NonlinearEquality1<VALUE> >
* Simple binary equality constraint - this constraint forces two variables to
* be the same.
*/
template<class VALUE>
class NonlinearEquality2: public NoiseModelFactor2<VALUE, VALUE> {
public:
typedef VALUE X;

protected:
typedef NoiseModelFactor2<VALUE, VALUE> Base;
typedef NonlinearEquality2<VALUE> This;
template <class T>
class NonlinearEquality2 : public NoiseModelFactor2<T, T> {
protected:
using Base = NoiseModelFactor2<T, T>;
using This = NonlinearEquality2<T>;

GTSAM_CONCEPT_MANIFOLD_TYPE(X)
GTSAM_CONCEPT_MANIFOLD_TYPE(T)

/// Default constructor to allow for serialization
NonlinearEquality2() {
}
NonlinearEquality2() {}

public:

typedef boost::shared_ptr<NonlinearEquality2<VALUE> > shared_ptr;
public:
typedef boost::shared_ptr<NonlinearEquality2<T>> shared_ptr;

/**
* Constructor
* @param key1 the key for the first unknown variable to be constrained
* @param key2 the key for the second unknown variable to be constrained
* @param mu a parameter which really turns this into a strong prior
*/
NonlinearEquality2(Key key1, Key key2, double mu = 1000.0) :
Base(noiseModel::Constrained::All(traits<X>::dimension, std::abs(mu)), key1, key2) {
}
~NonlinearEquality2() override {
}
NonlinearEquality2(Key key1, Key key2, double mu = 1e4)
: Base(noiseModel::Constrained::All(traits<T>::dimension, std::abs(mu)),
key1, key2) {}
~NonlinearEquality2() override {}

/// @return a deep copy of this factor
gtsam::NonlinearFactor::shared_ptr clone() const override {
Expand All @@ -328,32 +322,30 @@ class NonlinearEquality2: public NoiseModelFactor2<VALUE, VALUE> {
}

/// 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 override {
static const size_t p = traits<X>::dimension;
if (H1) *H1 = -Matrix::Identity(p,p);
if (H2) *H2 = Matrix::Identity(p,p);
return traits<X>::Local(x1,x2);
Vector evaluateError(
const T& x1, const T& x2, boost::optional<Matrix&> H1 = boost::none,
boost::optional<Matrix&> H2 = boost::none) const override {
static const size_t p = traits<T>::dimension;
if (H1) *H1 = -Matrix::Identity(p, p);
if (H2) *H2 = Matrix::Identity(p, p);
return traits<T>::Local(x1, x2);
}

GTSAM_MAKE_ALIGNED_OPERATOR_NEW

private:

private:
/// Serialization function
friend class boost::serialization::access;
template<class ARCHIVE>
void serialize(ARCHIVE & ar, const unsigned int /*version*/) {
ar
& boost::serialization::make_nvp("NoiseModelFactor2",
boost::serialization::base_object<Base>(*this));
template <class ARCHIVE>
void serialize(ARCHIVE& ar, const unsigned int /*version*/) {
ar& boost::serialization::make_nvp(
"NoiseModelFactor2", boost::serialization::base_object<Base>(*this));
}
};
// \NonlinearEquality2

template<typename VALUE>
struct traits<NonlinearEquality2<VALUE> > : Testable<NonlinearEquality2<VALUE> > {
template <typename VALUE>
struct traits<NonlinearEquality2<VALUE>> : Testable<NonlinearEquality2<VALUE>> {
};


}// namespace gtsam
13 changes: 13 additions & 0 deletions gtsam/nonlinear/nonlinear.i
Original file line number Diff line number Diff line change
Expand Up @@ -824,4 +824,17 @@ virtual class NonlinearEquality : gtsam::NoiseModelFactor {
void serialize() const;
};

template <T = {gtsam::Point2, gtsam::StereoPoint2, gtsam::Point3, gtsam::Rot2,
gtsam::SO3, gtsam::SO4, gtsam::SOn, gtsam::Rot3, gtsam::Pose2,
gtsam::Pose3, gtsam::Cal3_S2, gtsam::CalibratedCamera,
gtsam::PinholeCamera<gtsam::Cal3_S2>,
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think there could be a comment (or note) on what will be the name for this?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It will be NonlinearEquality2PinholeCameraCal3_S2. This should maybe go in gtwrap's docs?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah I agree

gtsam::PinholeCamera<gtsam::Cal3Bundler>,
gtsam::PinholeCamera<gtsam::Cal3Fisheye>,
gtsam::PinholeCamera<gtsam::Cal3Unified>,
gtsam::imuBias::ConstantBias}>
virtual class NonlinearEquality2 : gtsam::NoiseModelFactor {
NonlinearEquality2(Key key1, Key key2, double mu = 1e4);
gtsam::Vector evaluateError(const T& x1, const T& x2);
};

} // namespace gtsam
5 changes: 2 additions & 3 deletions python/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,5 @@ add_custom_target(
COMMAND
${CMAKE_COMMAND} -E env # add package to python path so no need to install
"PYTHONPATH=${GTSAM_PYTHON_BUILD_DIRECTORY}/$ENV{PYTHONPATH}"
${PYTHON_EXECUTABLE} -m unittest discover
DEPENDS ${GTSAM_PYTHON_DEPENDENCIES}
WORKING_DIRECTORY ${GTSAM_PYTHON_BUILD_DIRECTORY}/gtsam/tests)
${PYTHON_EXECUTABLE} -m unittest discover -s "${GTSAM_PYTHON_BUILD_DIRECTORY}/gtsam/tests"
DEPENDS ${GTSAM_PYTHON_DEPENDENCIES})
34 changes: 34 additions & 0 deletions python/gtsam/tests/test_Factors.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
"""
GTSAM Copyright 2010-2019, Georgia Tech Research Corporation,
Atlanta, Georgia 30332-0415
All Rights Reserved

See LICENSE for the license information

Unit tests for various factors.

Author: Varun Agrawal
"""
import unittest

import numpy as np

import gtsam
from gtsam.utils.test_case import GtsamTestCase


class TestNonlinearEquality2Factor(GtsamTestCase):
"""
Test various instantiations of NonlinearEquality2.
"""
def test_point3(self):
"""Test for Point3 version."""
factor = gtsam.NonlinearEquality2Point3(0, 1)
error = factor.evaluateError(gtsam.Point3(0, 0, 0),
gtsam.Point3(0, 0, 0))

np.testing.assert_allclose(error, np.zeros(3))


if __name__ == "__main__":
unittest.main()