This repository has been archived on 2026-03-28. You can view files and clone it, but you cannot make any changes to its state, such as pushing and creating new issues, pull requests or comments.
eodev/eo/src/serial/Utils.h

189 lines
6.1 KiB
C++

/*
(c) Thales group, 2012
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation;
version 2 of the License.
This library 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
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Contact: http://eodev.sourceforge.net
Authors:
Benjamin Bouvier <benjamin.bouvier@gmail.com>
*/
# ifndef __EOSERIAL_UTILS_H__
# define __EOSERIAL_UTILS_H__
# include "Array.h"
# include "Object.h"
# include "String.h"
namespace eoserial
{
/* ***************************
* DESERIALIZATION FUNCTIONS *
*****************************
These functions are useful for casting eoserial::objects into simple, primitive
variables or into class instance which implement eoserial::Persistent.
The model is always quite the same :
- the first argument is the containing object (which is a eoserial::Entity,
an object or an array)
- the second argument is the key or index,
- the last argument is the value in which we're writing.
*/
template< class T >
inline void unpack( const Object & obj, const std::string & key, T & value )
{
static_cast<String*>( obj.find( key )->second )->deserialize( value );
}
inline void unpackObject( const Object & obj, const std::string & key, Persistent & value )
{
static_cast<Object*>( obj.find( key )->second )->deserialize( value );
}
template< class Container, template<class> class UnpackAlgorithm >
inline void unpackArray( const Object & obj, const std::string & key, Container & array )
{
static_cast<Array*>( obj.find( key )->second )->deserialize< Container, UnpackAlgorithm >( array );
}
template< class T >
inline void unpack( const Array & array, unsigned int index, T & value )
{
static_cast<String*>( array[ index ] )->deserialize( value );
}
inline void unpackObject( const Array & array, unsigned int index, Persistent & value )
{
static_cast<Object*>( array[ index ] )->deserialize( value );
}
template< class Container, template<class> class UnpackAlgorithm >
inline void unpackArray( const Array & array, unsigned int index, Container & container )
{
static_cast<Array*>( array[ index ] )->deserialize< Container, UnpackAlgorithm >( container );
}
/* *****************************
*** SERIALIZATION FUNCTIONS ***
*******************************
These functions are useful for casting classic objects and
eoserial::Persistent objects into eoserial entities which
can be manipulated by the framework.
*/
/**
* @brief Casts a value of a stream-serializable type (i.e, which implements
* operator <<) into a JsonString.
*
* This is used when serializing the objects : all primitives types should be
* converted into strings to get more easily manipulated.
*
* @param value The value we're converting.
* @return JsonString wrapper for the value.
*/
template <typename T>
String* make( const T & value )
{
std::stringstream ss;
ss.precision(std::numeric_limits<double>::digits10 + 1);
ss << value;
return new String( ss.str() );
}
/**
* @brief Specialization for strings : no need to convert as they're still
* usable as strings.
*/
template<>
inline String* make( const std::string & value )
{
return new String( value );
}
/*
* These functions are useful for automatically serializing STL containers into
* eoserial arrays which could be used by the framework.
**/
/**
* @brief Functor which explains how to push the value into the eoserial::Array.
*/
template< class T >
struct PushAlgorithm
{
/**
* @brief Main operator.
*
* @param array The eoserial::array in which we're writing.
* @param value The variable we are writing.
*/
virtual void operator()( Array & array, const T & value ) = 0;
};
/**
* @brief Push algorithm for primitive variables.
*
* This one should be used when inserting primitive (and types which implement
* operator<<) variables.
*/
template< class T >
struct MakeAlgorithm : public PushAlgorithm<T>
{
void operator()( Array & array, const T & value )
{
array.push_back( make( value ) );
}
};
/**
* @brief Push algorithm for eoserial::Persistent variables.
*/
template< class T >
struct SerializablePushAlgorithm : public PushAlgorithm<T>
{
void operator()( Array & array, const T & obj )
{
// obj address is not saved into array.push_back.
array.push_back( &obj );
}
};
/**
* @brief Casts a STL container (vector<int> or list<std::string>, for instance)
* into a eoserial::Array.
*
* @þaram PushAlgorithm The algorithm used for inserting new element in the eoserial::Array.
* This algorithm is directly called, so it is its own charge to invoke push_back on the
* eoserial::Array.
*/
template< class Container, template<class> class PushAlgorithm >
Array* makeArray( const Container & array )
{
Array* returned_array = new Array;
typedef typename Container::const_iterator iterator;
typedef typename Container::value_type Type;
PushAlgorithm< Type > algo;
for (
iterator it = array.begin(), end = array.end();
it != end;
++it)
{
algo( *returned_array, *it );
}
return returned_array;
}
} // namespace eoserial
# endif //__EOSERIAL_UTILS_H__