mirror of
https://gitcode.com/gh_mirrors/ope/OpenFace.git
synced 2026-05-17 04:37:50 +00:00
Master commit of OpenFace.
This commit is contained in:
410
lib/3rdParty/dlib/include/dlib/tuple/tuple.h
vendored
Normal file
410
lib/3rdParty/dlib/include/dlib/tuple/tuple.h
vendored
Normal file
@@ -0,0 +1,410 @@
|
||||
// Copyright (C) 2007 Davis E. King (davis@dlib.net)
|
||||
// License: Boost Software License See LICENSE.txt for the full license.
|
||||
#ifndef DLIB_TUPLe_H_
|
||||
#define DLIB_TUPLe_H_
|
||||
|
||||
#include "../enable_if.h"
|
||||
#include "../algs.h"
|
||||
#include "../serialize.h"
|
||||
#include "tuple_abstract.h"
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
#define DLIB_TUPLE_GLOBAL_HELPERS(N) \
|
||||
DLIB_TUPLE_GH(N##0) DLIB_TUPLE_GH(N##1) DLIB_TUPLE_GH(N##2) DLIB_TUPLE_GH(N##3) \
|
||||
DLIB_TUPLE_GH(N##4) DLIB_TUPLE_GH(N##5) DLIB_TUPLE_GH(N##6) DLIB_TUPLE_GH(N##7)
|
||||
|
||||
#define DLIB_TUPLE_GH(N) DLIB_TUPLE_GET_INDEX(N) DLIB_TUPLE_GET_ITEM(N) DLIB_TUPLE_GET_HELPER_STRUCT(N)
|
||||
|
||||
#define DLIB_TUPLE_MEMBER_GET(N) \
|
||||
DLIB_TUPLE_MG(N##0) DLIB_TUPLE_MG(N##1) DLIB_TUPLE_MG(N##2) DLIB_TUPLE_MG(N##3) \
|
||||
DLIB_TUPLE_MG(N##4) DLIB_TUPLE_MG(N##5) DLIB_TUPLE_MG(N##6) DLIB_TUPLE_MG(N##7)
|
||||
|
||||
#define DLIB_TUPLE_GET_INDEX(N) \
|
||||
template <class Q, class T> const typename enable_if<is_same_type<typename T::type##N,Q>, long>::type get_index (const T&) {return N;}
|
||||
|
||||
#define DLIB_TUPLE_GET_ITEM(N) \
|
||||
template <class Q,class T> const typename enable_if<is_same_type<typename T::type##N,Q>,Q>::type& get_item_const (const T& t) {return t.v##N;}\
|
||||
template <class Q,class T> typename enable_if<is_same_type<typename T::type##N,Q>,Q>::type& get_item ( T& t) {return t.v##N;}
|
||||
|
||||
|
||||
#define DLIB_TUPLE_GET_HELPER_STRUCT(N) \
|
||||
template <class T> struct get_helper<N,T> \
|
||||
{ \
|
||||
typedef typename T::type##N type; \
|
||||
static const type& get(const T& t) { return t.v##N; } \
|
||||
static type& get( T& t) { return t.v##N; } \
|
||||
};
|
||||
|
||||
#define DLIB_TUPLE_TEMPLATE_LIST(N) \
|
||||
class T##N##0 = null_type, class T##N##1 = null_type, class T##N##2 = null_type, class T##N##3 = null_type, \
|
||||
class T##N##4 = null_type, class T##N##5 = null_type, class T##N##6 = null_type, class T##N##7 = null_type
|
||||
|
||||
#define DLIB_TUPLE_VARIABLE_LIST(N) \
|
||||
T##N##0 v##N##0; T##N##1 v##N##1; T##N##2 v##N##2; T##N##3 v##N##3; \
|
||||
T##N##4 v##N##4; T##N##5 v##N##5; T##N##6 v##N##6; T##N##7 v##N##7; \
|
||||
typedef T##N##0 type##N##0; typedef T##N##1 type##N##1; typedef T##N##2 type##N##2; \
|
||||
typedef T##N##3 type##N##3; typedef T##N##4 type##N##4; typedef T##N##5 type##N##5; \
|
||||
typedef T##N##6 type##N##6; typedef T##N##7 type##N##7;
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
namespace dlib
|
||||
{
|
||||
|
||||
struct null_type{};
|
||||
|
||||
// provide default serialization for the null_type
|
||||
inline void serialize (
|
||||
const null_type& ,
|
||||
std::ostream&
|
||||
){}
|
||||
inline void deserialize (
|
||||
null_type& ,
|
||||
std::istream&
|
||||
){}
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
namespace tuple_helpers
|
||||
{
|
||||
template <long idx, class T> struct get_helper;
|
||||
|
||||
// use these preprocessor macros to declare all the global stuff used by the
|
||||
// tuple member functions.
|
||||
DLIB_TUPLE_GLOBAL_HELPERS(0)
|
||||
DLIB_TUPLE_GLOBAL_HELPERS(01)
|
||||
DLIB_TUPLE_GLOBAL_HELPERS(02)
|
||||
DLIB_TUPLE_GLOBAL_HELPERS(03)
|
||||
|
||||
// ------------------------------------------------------------------------------------
|
||||
|
||||
// use templates to recursively enumerate everything in the tuple that isn't a null_type
|
||||
template <
|
||||
typename T,
|
||||
typename F,
|
||||
long i = 0,
|
||||
typename enabled = void
|
||||
>
|
||||
struct for_each
|
||||
{
|
||||
static void go(
|
||||
T& a,
|
||||
F& funct
|
||||
)
|
||||
{
|
||||
funct(a.template get<i>());
|
||||
for_each<T,F,i+1>::go(a,funct);
|
||||
}
|
||||
|
||||
static bool go(
|
||||
T& a,
|
||||
F& funct,
|
||||
long idx
|
||||
)
|
||||
/*!
|
||||
ensures
|
||||
- returns true if the function was applied to the given index
|
||||
- returns false if the index is invalid so the function wasn't
|
||||
applied to anything
|
||||
!*/
|
||||
{
|
||||
if (idx == i)
|
||||
{
|
||||
funct(a.template get<i>());
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
return for_each<T,F,i+1>::go(a,funct,idx);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
template <bool v1, bool v2> struct template_or { const static bool value = true; };
|
||||
template <> struct template_or<false,false> { const static bool value = false; };
|
||||
|
||||
// the base case of the recursion
|
||||
template <
|
||||
typename T,
|
||||
typename F,
|
||||
long i
|
||||
>
|
||||
struct for_each<T,F,i,typename enable_if<template_or<i == T::max_fields , is_same_type<null_type,typename T::template get_type<i>::type >::value> >::type >
|
||||
{
|
||||
static void go( T&, F& ) { }
|
||||
static bool go( T&, F&, long ) { return false; }
|
||||
};
|
||||
|
||||
// ------------------------------------------------------------------------------------
|
||||
|
||||
// use templates to recursively enumerate everything in the tuple that isn't a null_type
|
||||
template <
|
||||
typename T,
|
||||
long i = 0,
|
||||
typename enabled = void
|
||||
>
|
||||
struct tuple_swap
|
||||
{
|
||||
static void go(
|
||||
T& a,
|
||||
T& b
|
||||
)
|
||||
{
|
||||
exchange(a.template get<i>(), b.template get<i>());
|
||||
tuple_swap<T,i+1>::go(a,b);
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T, long i>
|
||||
struct at_base_case
|
||||
{
|
||||
|
||||
};
|
||||
|
||||
// the base case of the recursion
|
||||
template <
|
||||
typename T,
|
||||
long i
|
||||
>
|
||||
struct tuple_swap<T,i,typename enable_if<template_or<i == T::max_fields, is_same_type<null_type,typename T::template get_type<i>::type >::value > >::type >
|
||||
{ static void go( T&, T& ) { } };
|
||||
|
||||
// ------------------------------------------------------------------------------------
|
||||
|
||||
struct tuple_serialize
|
||||
{
|
||||
tuple_serialize (std::ostream& out_) : out(out_){}
|
||||
std::ostream& out;
|
||||
|
||||
template <typename T>
|
||||
void operator() (
|
||||
T& a
|
||||
) const { serialize(a,out); }
|
||||
};
|
||||
|
||||
// ------------------------------------------------------------------------------------
|
||||
|
||||
struct tuple_deserialize
|
||||
{
|
||||
tuple_deserialize (std::istream& in_) : in(in_){}
|
||||
std::istream& in;
|
||||
template <typename T>
|
||||
void operator() (
|
||||
T& a
|
||||
) const { deserialize(a,in); }
|
||||
};
|
||||
|
||||
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
// use these preprocessor macros to declare 4*8 template arguments (below we count them in octal)
|
||||
template <
|
||||
DLIB_TUPLE_TEMPLATE_LIST(0), // args 00-07
|
||||
DLIB_TUPLE_TEMPLATE_LIST(01), // args 010-017
|
||||
DLIB_TUPLE_TEMPLATE_LIST(02), // args 020-027
|
||||
DLIB_TUPLE_TEMPLATE_LIST(03) // args 030-037
|
||||
>
|
||||
class tuple
|
||||
{
|
||||
public:
|
||||
|
||||
// use these macros to declare 8*4 member variables
|
||||
DLIB_TUPLE_VARIABLE_LIST(0)
|
||||
DLIB_TUPLE_VARIABLE_LIST(01)
|
||||
DLIB_TUPLE_VARIABLE_LIST(02)
|
||||
DLIB_TUPLE_VARIABLE_LIST(03)
|
||||
|
||||
const static long max_fields = 4*8;
|
||||
|
||||
template < long idx >
|
||||
struct get_type
|
||||
{
|
||||
typedef typename tuple_helpers::get_helper<idx,tuple>::type type;
|
||||
};
|
||||
|
||||
template < long idx >
|
||||
const typename tuple_helpers::get_helper<idx,tuple>::type& get (
|
||||
) const { return tuple_helpers::get_helper<idx,tuple>::get(*this); }
|
||||
|
||||
template < long idx >
|
||||
typename tuple_helpers::get_helper<idx,tuple>::type& get (
|
||||
) { return tuple_helpers::get_helper<idx,tuple>::get(*this); }
|
||||
|
||||
template < class Q>
|
||||
long index (
|
||||
) const { return tuple_helpers::get_index<Q>(*this); }
|
||||
|
||||
template <class Q>
|
||||
const Q& get (
|
||||
) const {return tuple_helpers::get_item_const<Q>(*this);}
|
||||
|
||||
template <class Q>
|
||||
Q& get (
|
||||
) {return tuple_helpers::get_item<Q>(*this);}
|
||||
|
||||
|
||||
|
||||
|
||||
template <typename F>
|
||||
void for_index (
|
||||
F& funct,
|
||||
long idx
|
||||
)
|
||||
{
|
||||
// do this #ifdef stuff to avoid getting a warning about valid_idx not being
|
||||
// used when ENABLE_ASSERTS isn't defined.
|
||||
#ifdef ENABLE_ASSERTS
|
||||
const bool valid_idx = tuple_helpers::for_each<tuple,F>::go(*this,funct,idx);
|
||||
#else
|
||||
tuple_helpers::for_each<tuple,F>::go(*this,funct,idx);
|
||||
#endif
|
||||
DLIB_ASSERT(valid_idx,
|
||||
"\tvoid tuple::for_index()"
|
||||
<< "\n\tYou have attempted to call for_index() with an index out of the valid range"
|
||||
<< "\n\tidx: " << idx
|
||||
<< "\n\tthis: " << this
|
||||
);
|
||||
}
|
||||
|
||||
template <typename F>
|
||||
void for_index (
|
||||
F& funct,
|
||||
long idx
|
||||
) const
|
||||
{
|
||||
// do this #ifdef stuff to avoid getting a warning about valid_idx not being
|
||||
// used when ENABLE_ASSERTS isn't defined.
|
||||
#ifdef ENABLE_ASSERTS
|
||||
const bool valid_idx = tuple_helpers::for_each<const tuple,F>::go(*this,funct,idx);
|
||||
#else
|
||||
tuple_helpers::for_each<const tuple,F>::go(*this,funct,idx);
|
||||
#endif
|
||||
DLIB_ASSERT(valid_idx,
|
||||
"\tvoid tuple::for_index()"
|
||||
<< "\n\tYou have attempted to call for_index() with an index out of the valid range"
|
||||
<< "\n\tidx: " << idx
|
||||
<< "\n\tthis: " << this
|
||||
);
|
||||
}
|
||||
|
||||
template <typename F>
|
||||
void for_index (
|
||||
const F& funct,
|
||||
long idx
|
||||
)
|
||||
{
|
||||
// do this #ifdef stuff to avoid getting a warning about valid_idx not being
|
||||
// used when ENABLE_ASSERTS isn't defined.
|
||||
#ifdef ENABLE_ASSERTS
|
||||
const bool valid_idx = tuple_helpers::for_each<tuple,const F>::go(*this,funct,idx);
|
||||
#else
|
||||
tuple_helpers::for_each<tuple,const F>::go(*this,funct,idx);
|
||||
#endif
|
||||
DLIB_ASSERT(valid_idx,
|
||||
"\tvoid tuple::for_index()"
|
||||
<< "\n\tYou have attempted to call for_index() with an index out of the valid range"
|
||||
<< "\n\tidx: " << idx
|
||||
<< "\n\tthis: " << this
|
||||
);
|
||||
}
|
||||
|
||||
template <typename F>
|
||||
void for_index (
|
||||
const F& funct,
|
||||
long idx
|
||||
) const
|
||||
{
|
||||
// do this #ifdef stuff to avoid getting a warning about valid_idx not being
|
||||
// used when ENABLE_ASSERTS isn't defined.
|
||||
#ifdef ENABLE_ASSERTS
|
||||
const bool valid_idx = tuple_helpers::for_each<const tuple,const F>::go(*this,funct,idx);
|
||||
#else
|
||||
tuple_helpers::for_each<const tuple,const F>::go(*this,funct,idx);
|
||||
#endif
|
||||
DLIB_ASSERT(valid_idx,
|
||||
"\tvoid tuple::for_index()"
|
||||
<< "\n\tYou have attempted to call for_index() with an index out of the valid range"
|
||||
<< "\n\tidx: " << idx
|
||||
<< "\n\tthis: " << this
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
template <typename F>
|
||||
void for_each (
|
||||
F& funct
|
||||
) { tuple_helpers::for_each<tuple,F>::go(*this,funct); }
|
||||
|
||||
template <typename F>
|
||||
void for_each (
|
||||
F& funct
|
||||
) const { tuple_helpers::for_each<const tuple,F>::go(*this,funct); }
|
||||
|
||||
template <typename F>
|
||||
void for_each (
|
||||
const F& funct
|
||||
) const { tuple_helpers::for_each<const tuple,const F>::go(*this,funct); }
|
||||
|
||||
template <typename F>
|
||||
void for_each (
|
||||
const F& funct
|
||||
) { tuple_helpers::for_each<tuple,const F>::go(*this,funct); }
|
||||
|
||||
|
||||
|
||||
|
||||
inline friend void serialize (
|
||||
tuple& item,
|
||||
std::ostream& out
|
||||
)
|
||||
{
|
||||
try
|
||||
{
|
||||
item.for_each(tuple_helpers::tuple_serialize(out));
|
||||
}
|
||||
catch (serialization_error& e)
|
||||
{
|
||||
throw serialization_error(e.info + "\n while serializing an object of type dlib::tuple<>");
|
||||
}
|
||||
}
|
||||
|
||||
inline friend void deserialize (
|
||||
tuple& item,
|
||||
std::istream& in
|
||||
)
|
||||
{
|
||||
try
|
||||
{
|
||||
item.for_each(tuple_helpers::tuple_deserialize(in));
|
||||
}
|
||||
catch (serialization_error& e)
|
||||
{
|
||||
throw serialization_error(e.info + "\n while deserializing an object of type dlib::tuple<>");
|
||||
}
|
||||
}
|
||||
|
||||
inline friend void swap (
|
||||
tuple& a,
|
||||
tuple& b
|
||||
)
|
||||
{
|
||||
tuple_helpers::tuple_swap<tuple>::go(a,b);
|
||||
}
|
||||
|
||||
inline void swap(
|
||||
tuple& item
|
||||
) { tuple_helpers::tuple_swap<tuple>::go(item,*this); }
|
||||
|
||||
};
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
}
|
||||
|
||||
#endif // DLIB_TUPLe_H_
|
||||
|
||||
Reference in New Issue
Block a user