Sophie

Sophie

distrib > Fedora > 16 > i386 > by-pkgid > 4bc66056a634db26a1f4d0845dc41ca6 > files > 15737

mrpt-doc-0.9.5-0.1.20110925svn2670.fc16.i686.rpm

/* +---------------------------------------------------------------------------+
   |          The Mobile Robot Programming Toolkit (MRPT) C++ library          |
   |                                                                           |
   |                       http://www.mrpt.org/                                |
   |                                                                           |
   |   Copyright (C) 2005-2011  University of Malaga                           |
   |                                                                           |
   |    This software was written by the Machine Perception and Intelligent    |
   |      Robotics Lab, University of Malaga (Spain).                          |
   |    Contact: Jose-Luis Blanco  <jlblanco@ctima.uma.es>                     |
   |                                                                           |
   |  This file is part of the MRPT project.                                   |
   |                                                                           |
   |     MRPT is free software: you can redistribute it and/or modify          |
   |     it under the terms of the GNU General Public License as published by  |
   |     the Free Software Foundation, either version 3 of the License, or     |
   |     (at your option) any later version.                                   |
   |                                                                           |
   |   MRPT is distributed in the hope that it will be useful,                 |
   |     but WITHOUT ANY WARRANTY; without even the implied warranty of        |
   |     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         |
   |     GNU General Public License for more details.                          |
   |                                                                           |
   |     You should have received a copy of the GNU General Public License     |
   |     along with MRPT.  If not, see <http://www.gnu.org/licenses/>.         |
   |                                                                           |
   +---------------------------------------------------------------------------+ */

#include <mrpt/base.h>
#include <mrpt/slam.h>
#include <mrpt/gui.h>

using namespace mrpt;
using namespace mrpt::utils;
using namespace mrpt::math;
using namespace std;


// Example non-linear function for SUT
//   f: R^5   => R^3
void  myFun1(const  CArrayDouble<5> &x,const double &user_param, CArrayDouble<3> &y )
{
	y[0] = cos(x[0])*exp(x[1])+x[4];
	y[1] = x[1]/(1+square(x[0]));
	y[2] = x[4]/(1+square(x[3])) + sin(x[1]*x[0]);
}

CArrayDouble<7>::iterator it = CArrayDouble<7>::iterator();

/* ------------------------------------------------------------------------
					Test_SUT: Scaled Unscented Transform
   ------------------------------------------------------------------------ */
void Test_SUT()
{
	// Inputs:
	const double x0[] = {1.8,0.7,0.9,-5.6,8.9};
	const double x0cov[] = {
		0.049400,0.011403,-0.006389,0.008132,-0.008595,
		0.011403,0.026432,0.005382,0.008622,-0.017399,
		-0.006389,0.005382,0.063268,-0.019310,-0.017868,
		0.008132,0.008622,-0.019310,0.028474,0.003507,
		-0.008595,-0.017399,-0.017868,0.003507,0.17398  };

	const CArrayDouble<5>  x_mean(x0);
	const CMatrixFixedNumeric<double,5,5>  x_cov(x0cov);
	const double dumm=0;

	// Outputs:
	CArrayDouble<3> y_mean;
	CMatrixDouble33 y_cov;


	// Do SUT:
	CTicTac tictac;
	size_t N = 10000;

	tictac.Tic();
	for (size_t i=0;i<N;i++)
		mrpt::math::transform_gaussian_unscented(
			x_mean, x_cov,
			myFun1,
			dumm, // fixed parameter: not used in this example
			y_mean,y_cov
			);

	cout << "SUT: Time (ms): " << 1e3*tictac.Tac()/N<< endl;

	// Print:
	cout << " ======= Scaled Unscented Transform ======== " << endl;
	cout << "y_mean: " << y_mean << endl;
	cout << "y_cov: "  << endl << y_cov << endl << endl;

	// 3D view:
	mrpt::opengl::COpenGLScenePtr scene = mrpt::opengl::COpenGLScene::Create();
	scene->insert( opengl::CGridPlaneXY::Create(-10,10,-10,10, 0, 1));

	{
		opengl::CEllipsoidPtr el = opengl::CEllipsoid::Create();
		el->enableDrawSolid3D(false);
		el->setLocation(y_mean[0],y_mean[1],y_mean[2]);
		el->setCovMatrix(y_cov);
		el->setColor(0,0,1);
		scene->insert(el);
	}

	// Do Montecarlo for comparison:
	N = 10;

	mrpt::aligned_containers<CArrayDouble<3> >::vector_t MC_samples;

	tictac.Tic();
	for (size_t i=0;i<N;i++)
		mrpt::math::transform_gaussian_montecarlo(
			x_mean, x_cov,
			myFun1,
			dumm, // fixed parameter: not used in this example
			y_mean,y_cov,
			5e5,  // Samples
			&MC_samples  // we want the samples.
			);

	cout << "MC: Time (ms): " << 1e3*tictac.Tac()/N<< endl;


	vector_double MC_y[3];

	for (int i=0;i<3;i++)
		extractColumnFromVectorOfVectors(i,MC_samples,MC_y[i]);

	{
		opengl::CEllipsoidPtr el = opengl::CEllipsoid::Create();
		el->enableDrawSolid3D(false);
		el->setLocation(y_mean[0],y_mean[1],y_mean[2]);
		el->setCovMatrix(y_cov);
		el->setColor(0,1,0);
		scene->insert(el);
	}

	// Print:
	cout << " ======= Montecarlo Transform ======== " << endl;
	cout << "y_mean: " << y_mean << endl;
	cout << "y_cov: "  << endl << y_cov << endl;

	// Do Linear for comparison:
	N = 100;

	CArrayDouble<5> x_incrs;
	x_incrs.fill(1e-6);

	tictac.Tic();
	for (size_t i=0;i<N;i++)
		mrpt::math::transform_gaussian_linear(
			x_mean, x_cov,
			myFun1,
			dumm, // fixed parameter: not used in this example
			y_mean,y_cov,
			x_incrs
			);

	cout << "LIN: Time (ms): " << 1e3*tictac.Tac()/N<< endl;

	// Print:
	cout << " ======= Linear Transform ======== " << endl;
	cout << "y_mean: " << y_mean << endl;
	cout << "y_cov: "  << endl << y_cov << endl;

	{
		opengl::CEllipsoidPtr el = opengl::CEllipsoid::Create();
		el->enableDrawSolid3D(false);
		el->setLocation(y_mean[0],y_mean[1],y_mean[2]);
		el->setCovMatrix(y_cov);
		el->setColor(1,0,0);
		scene->insert(el);
	}


	mrpt::gui::CDisplayWindow3D  win("Comparison SUT (blue), Linear (red), MC (green)",400,300);
	win.get3DSceneAndLock() = scene;
	win.unlockAccess3DScene();


	win.setCameraPointingToPoint(y_mean[0],y_mean[1],y_mean[2]);
	win.setCameraZoom(5.0);


	// MC-based histograms:
	mrpt::gui::CDisplayWindowPlotsPtr  winHistos[3];

	for (int i=0;i<3;i++)
	{
		winHistos[i] = mrpt::gui::CDisplayWindowPlots::Create(format("MC-based histogram of the %i dim",i),300,150);

		vector_double  X;
		vector_double  H = mrpt::math::histogram(MC_y[i],MC_y[i].minimum(),MC_y[i].maximum(),40, true, &X);

		winHistos[i]->plot(X,H,"b");
		winHistos[i]->axis_fit();
	}


	win.forceRepaint();

	cout << endl << "Press any key to exit" << endl;
	win.waitForKey();
}


// Calibration of SUT parameters for Quat -> 3D pose
// -----------------------------------------------------------

void aux_posequat2poseypr(const CArrayDouble<7> &x,const double&dummy, CArrayDouble<6> &y)
{
	const CPose3DQuat p(x[0],x[1],x[2], mrpt::math::CQuaternionDouble(x[3],x[4],x[5],x[6]) );
	const CPose3D p2 = CPose3D(p);
	for (int i=0;i<6;i++)
		y[i]=p2[i];
	//cout << "p2: " << y[3] << endl;
}

void TestCalibrate_pose2quat()
{
	// Take a 7x7 representation:
	CPose3DQuatPDFGaussian  o;
	o.mean = CPose3DQuat(CPose3D(1.0,2.0,3.0, DEG2RAD(-30),DEG2RAD(10),DEG2RAD(60)));
	//o.mean = CPose3D(1.0,2.0,3.0, DEG2RAD(00),DEG2RAD(90),DEG2RAD(0));

	CMatrixFixedNumeric<double,7,1> v;
	mrpt::random::randomGenerator.drawGaussian1DMatrix(v);
	v*=1e-3;
	o.cov.multiply_AAt(v);  // COV = v*vt
	for (int i=0;i<7;i++)
		o.cov(i,i)+=0.01;

	o.cov(0,1)=o.cov(1,0)=0.007;

	cout << "p1quat: " << endl << o << endl;

	// Use UT transformation:
	//   f: R^7 => R^6
	const CArrayDouble<7> x_mean(o.mean);
	CArrayDouble<6> y_mean;
	static const bool elements_do_wrapPI[6] = {false,false,false,true,true,true};  // xyz yaw pitch roll


	static const double dummy=0;
	// MonteCarlo:
	CArrayDouble<6> MC_y_mean;
	CMatrixDouble66 MC_y_cov;
	mrpt::math::transform_gaussian_montecarlo(
		x_mean, o.cov,
		aux_posequat2poseypr,
		dummy, // fixed parameter: not used in this example
		MC_y_mean,MC_y_cov,
		500
		);
	cout << "MC: " << endl << MC_y_mean << endl << endl << MC_y_cov << endl << endl;

	// SUT:

	CPose3DPDFGaussian  p_ypr;

	//double  = 1e-3;
	//alpha = x_mean.size()-3;

	mrpt::math::transform_gaussian_unscented(
		x_mean, o.cov,
		aux_posequat2poseypr,
		dummy,
		y_mean,
		p_ypr.cov,
		elements_do_wrapPI,
		1e-3,  // alpha
		0,     // K
		2.0    // beta
		);

	cout << "SUT: " << endl << y_mean << endl << endl << p_ypr.cov << endl << endl;


}

// ------------------------------------------------------
//						MAIN
// ------------------------------------------------------
int main(int argc, char **argv)
{
	try
	{
		Test_SUT();

		//TestCalibrate_pose2quat();

		return 0;
	} catch (std::exception &e)
	{
		std::cout << "Exception: " << e.what() << std::endl;
		return -1;
	}
	catch (...)
	{
		printf("Untyped exception!");
		return -1;
	}
}