Initial Commit - Lesson 31 (Commit #1)
This commit is contained in:
@@ -0,0 +1,774 @@
|
||||
// Copyright (C) 2008 Davis E. King (davis@dlib.net)
|
||||
// License: Boost Software License See LICENSE.txt for the full license.
|
||||
#ifndef DLIB_BOUND_FUNCTION_POINTER_KERNEl_1_
|
||||
#define DLIB_BOUND_FUNCTION_POINTER_KERNEl_1_
|
||||
|
||||
#include "../algs.h"
|
||||
#include "../member_function_pointer.h"
|
||||
#include "bound_function_pointer_kernel_abstract.h"
|
||||
|
||||
namespace dlib
|
||||
{
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
namespace bfp1_helpers
|
||||
{
|
||||
template <typename T> struct strip { typedef T type; };
|
||||
template <typename T> struct strip<T&> { typedef T type; };
|
||||
|
||||
// ------------------------------------------------------------------------------------
|
||||
|
||||
class bound_function_helper_base_base
|
||||
{
|
||||
public:
|
||||
virtual ~bound_function_helper_base_base(){}
|
||||
virtual void call() const = 0;
|
||||
virtual bool is_set() const = 0;
|
||||
virtual void clone(void* ptr) const = 0;
|
||||
};
|
||||
|
||||
// ------------------------------------------------------------------------------------
|
||||
|
||||
template <typename T1, typename T2, typename T3, typename T4>
|
||||
class bound_function_helper_base : public bound_function_helper_base_base
|
||||
{
|
||||
public:
|
||||
bound_function_helper_base():arg1(0), arg2(0), arg3(0), arg4(0) {}
|
||||
|
||||
typename strip<T1>::type* arg1;
|
||||
typename strip<T2>::type* arg2;
|
||||
typename strip<T3>::type* arg3;
|
||||
typename strip<T4>::type* arg4;
|
||||
|
||||
|
||||
member_function_pointer<T1,T2,T3,T4> mfp;
|
||||
};
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename F, typename T1 = void, typename T2 = void, typename T3 = void, typename T4 = void>
|
||||
class bound_function_helper : public bound_function_helper_base<T1,T2,T3,T4>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
(*fp)(*this->arg1, *this->arg2, *this->arg3, *this->arg4);
|
||||
}
|
||||
|
||||
typename strip<F>::type* fp;
|
||||
};
|
||||
|
||||
template <typename T1, typename T2, typename T3, typename T4>
|
||||
class bound_function_helper<void,T1,T2,T3,T4> : public bound_function_helper_base<T1,T2,T3,T4>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
if (this->mfp) this->mfp(*this->arg1, *this->arg2, *this->arg3, *this->arg4);
|
||||
else if (fp) fp(*this->arg1, *this->arg2, *this->arg3, *this->arg4);
|
||||
}
|
||||
|
||||
void (*fp)(T1, T2, T3, T4);
|
||||
};
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename F>
|
||||
class bound_function_helper<F,void,void,void,void> : public bound_function_helper_base<void,void,void,void>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
(*fp)();
|
||||
}
|
||||
|
||||
typename strip<F>::type* fp;
|
||||
};
|
||||
|
||||
template <>
|
||||
class bound_function_helper<void,void,void,void,void> : public bound_function_helper_base<void,void,void,void>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
if (this->mfp) this->mfp();
|
||||
else if (fp) fp();
|
||||
}
|
||||
|
||||
void (*fp)();
|
||||
};
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename F, typename T1>
|
||||
class bound_function_helper<F,T1,void,void,void> : public bound_function_helper_base<T1,void,void,void>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
(*fp)(*this->arg1);
|
||||
}
|
||||
|
||||
typename strip<F>::type* fp;
|
||||
};
|
||||
|
||||
template <typename T1>
|
||||
class bound_function_helper<void,T1,void,void,void> : public bound_function_helper_base<T1,void,void,void>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
if (this->mfp) this->mfp(*this->arg1);
|
||||
else if (fp) fp(*this->arg1);
|
||||
}
|
||||
|
||||
void (*fp)(T1);
|
||||
};
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename F, typename T1, typename T2>
|
||||
class bound_function_helper<F,T1,T2,void,void> : public bound_function_helper_base<T1,T2,void,void>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
(*fp)(*this->arg1, *this->arg2);
|
||||
}
|
||||
|
||||
typename strip<F>::type* fp;
|
||||
};
|
||||
|
||||
template <typename T1, typename T2>
|
||||
class bound_function_helper<void,T1,T2,void,void> : public bound_function_helper_base<T1,T2,void,void>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
if (this->mfp) this->mfp(*this->arg1, *this->arg2);
|
||||
else if (fp) fp(*this->arg1, *this->arg2);
|
||||
}
|
||||
|
||||
void (*fp)(T1, T2);
|
||||
};
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename F, typename T1, typename T2, typename T3>
|
||||
class bound_function_helper<F,T1,T2,T3,void> : public bound_function_helper_base<T1,T2,T3,void>
|
||||
{
|
||||
public:
|
||||
void call() const
|
||||
{
|
||||
(*fp)(*this->arg1, *this->arg2, *this->arg3);
|
||||
}
|
||||
|
||||
typename strip<F>::type* fp;
|
||||
};
|
||||
|
||||
template <typename T1, typename T2, typename T3>
|
||||
class bound_function_helper<void,T1,T2,T3,void> : public bound_function_helper_base<T1,T2,T3,void>
|
||||
{
|
||||
public:
|
||||
|
||||
void call() const
|
||||
{
|
||||
if (this->mfp) this->mfp(*this->arg1, *this->arg2, *this->arg3);
|
||||
else if (fp) fp(*this->arg1, *this->arg2, *this->arg3);
|
||||
}
|
||||
|
||||
void (*fp)(T1, T2, T3);
|
||||
};
|
||||
|
||||
// ------------------------------------------------------------------------------------
|
||||
// ------------------------------------------------------------------------------------
|
||||
|
||||
template <typename T>
|
||||
class bound_function_helper_T : public T
|
||||
{
|
||||
public:
|
||||
bound_function_helper_T(){ this->fp = 0;}
|
||||
|
||||
bool is_set() const
|
||||
{
|
||||
return this->fp != 0 || this->mfp.is_set();
|
||||
}
|
||||
|
||||
template <unsigned long mem_size>
|
||||
void safe_clone(stack_based_memory_block<mem_size>& buf)
|
||||
{
|
||||
// This is here just to validate the assumption that our block of memory we have made
|
||||
// in bf_memory is the right size to store the data for this object. If you
|
||||
// get a compiler error on this line then email me :)
|
||||
COMPILE_TIME_ASSERT(sizeof(bound_function_helper_T) <= mem_size);
|
||||
clone(buf.get());
|
||||
}
|
||||
|
||||
void clone (void* ptr) const
|
||||
{
|
||||
bound_function_helper_T* p = new(ptr) bound_function_helper_T();
|
||||
p->arg1 = this->arg1;
|
||||
p->arg2 = this->arg2;
|
||||
p->arg3 = this->arg3;
|
||||
p->arg4 = this->arg4;
|
||||
p->fp = this->fp;
|
||||
p->mfp = this->mfp;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
class bound_function_pointer
|
||||
{
|
||||
typedef bfp1_helpers::bound_function_helper_T<bfp1_helpers::bound_function_helper<void,int> > bf_null_type;
|
||||
|
||||
public:
|
||||
|
||||
// These typedefs are here for backwards compatibility with previous versions of
|
||||
// dlib.
|
||||
typedef bound_function_pointer kernel_1a;
|
||||
typedef bound_function_pointer kernel_1a_c;
|
||||
|
||||
|
||||
bound_function_pointer (
|
||||
) { bf_null_type().safe_clone(bf_memory); }
|
||||
|
||||
bound_function_pointer (
|
||||
const bound_function_pointer& item
|
||||
) { item.bf()->clone(bf_memory.get()); }
|
||||
|
||||
~bound_function_pointer()
|
||||
{ destroy_bf_memory(); }
|
||||
|
||||
bound_function_pointer& operator= (
|
||||
const bound_function_pointer& item
|
||||
) { bound_function_pointer(item).swap(*this); return *this; }
|
||||
|
||||
void clear (
|
||||
) { bound_function_pointer().swap(*this); }
|
||||
|
||||
bool is_set (
|
||||
) const
|
||||
{
|
||||
return bf()->is_set();
|
||||
}
|
||||
|
||||
void swap (
|
||||
bound_function_pointer& item
|
||||
)
|
||||
{
|
||||
// make a temp copy of item
|
||||
bound_function_pointer temp(item);
|
||||
|
||||
// destory the stuff in item
|
||||
item.destroy_bf_memory();
|
||||
// copy *this into item
|
||||
bf()->clone(item.bf_memory.get());
|
||||
|
||||
// destory the stuff in this
|
||||
destroy_bf_memory();
|
||||
// copy temp into *this
|
||||
temp.bf()->clone(bf_memory.get());
|
||||
}
|
||||
|
||||
void operator() (
|
||||
) const
|
||||
{
|
||||
// make sure requires clause is not broken
|
||||
DLIB_ASSERT(is_set() == true ,
|
||||
"\tvoid bound_function_pointer::operator()"
|
||||
<< "\n\tYou must call set() before you can use this function"
|
||||
<< "\n\tthis: " << this
|
||||
);
|
||||
|
||||
bf()->call();
|
||||
}
|
||||
|
||||
private:
|
||||
struct dummy{ void nonnull() {}};
|
||||
typedef void (dummy::*safe_bool)();
|
||||
|
||||
public:
|
||||
operator safe_bool () const { return is_set() ? &dummy::nonnull : 0; }
|
||||
bool operator!() const { return !is_set(); }
|
||||
|
||||
// -------------------------------------------
|
||||
// set function object overloads
|
||||
// -------------------------------------------
|
||||
|
||||
template <typename F>
|
||||
void set (
|
||||
F& function_object
|
||||
)
|
||||
{
|
||||
COMPILE_TIME_ASSERT(is_function<F>::value == false);
|
||||
COMPILE_TIME_ASSERT(is_pointer_type<F>::value == false);
|
||||
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<F> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.fp = &function_object;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename F, typename A1 >
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1
|
||||
)
|
||||
{
|
||||
COMPILE_TIME_ASSERT(is_function<F>::value == false);
|
||||
COMPILE_TIME_ASSERT(is_pointer_type<F>::value == false);
|
||||
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<F,A1> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.fp = &function_object;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename F, typename A1, typename A2 >
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
)
|
||||
{
|
||||
COMPILE_TIME_ASSERT(is_function<F>::value == false);
|
||||
COMPILE_TIME_ASSERT(is_pointer_type<F>::value == false);
|
||||
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<F,A1,A2> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.fp = &function_object;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename F, typename A1, typename A2, typename A3 >
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
)
|
||||
{
|
||||
COMPILE_TIME_ASSERT(is_function<F>::value == false);
|
||||
COMPILE_TIME_ASSERT(is_pointer_type<F>::value == false);
|
||||
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<F,A1,A2,A3> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.fp = &function_object;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename F, typename A1, typename A2, typename A3, typename A4>
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
)
|
||||
{
|
||||
COMPILE_TIME_ASSERT(is_function<F>::value == false);
|
||||
COMPILE_TIME_ASSERT(is_pointer_type<F>::value == false);
|
||||
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<F,A1,A2,A3,A4> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.arg4 = &arg4;
|
||||
temp.fp = &function_object;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
// -------------------------------------------
|
||||
// set mfp overloads
|
||||
// -------------------------------------------
|
||||
|
||||
template <typename T>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)()
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T >
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)()const
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
// -------------------------------------------
|
||||
|
||||
template <typename T, typename T1, typename A1 >
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1),
|
||||
A1& arg1
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T, typename T1, typename A1 >
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1)const,
|
||||
A1& arg1
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename T, typename T1, typename A1,
|
||||
typename T2, typename A2>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1, T2),
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T, typename T1, typename A1,
|
||||
typename T2, typename A2>
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1, T2)const,
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1, T2, T3),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2,T3> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3>
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1, T2, T3)const,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2,T3> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
// ----------------
|
||||
|
||||
template <typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3,
|
||||
typename T4, typename A4>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1, T2, T3, T4),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2,T3,T4> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.arg4 = &arg4;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3,
|
||||
typename T4, typename A4>
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1, T2, T3, T4)const,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2,T3,T4> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.arg4 = &arg4;
|
||||
temp.mfp.set(object,funct);
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
// -------------------------------------------
|
||||
// set fp overloads
|
||||
// -------------------------------------------
|
||||
|
||||
void set (
|
||||
void (*funct)()
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.fp = funct;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T1, typename A1>
|
||||
void set (
|
||||
void (*funct)(T1),
|
||||
A1& arg1
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.fp = funct;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T1, typename A1,
|
||||
typename T2, typename A2>
|
||||
void set (
|
||||
void (*funct)(T1, T2),
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.fp = funct;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3>
|
||||
void set (
|
||||
void (*funct)(T1, T2, T3),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2,T3> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.fp = funct;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
template <typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3,
|
||||
typename T4, typename A4>
|
||||
void set (
|
||||
void (*funct)(T1, T2, T3, T4),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
)
|
||||
{
|
||||
using namespace bfp1_helpers;
|
||||
destroy_bf_memory();
|
||||
typedef bound_function_helper_T<bound_function_helper<void,T1,T2,T3,T4> > bf_helper_type;
|
||||
|
||||
bf_helper_type temp;
|
||||
temp.arg1 = &arg1;
|
||||
temp.arg2 = &arg2;
|
||||
temp.arg3 = &arg3;
|
||||
temp.arg4 = &arg4;
|
||||
temp.fp = funct;
|
||||
|
||||
temp.safe_clone(bf_memory);
|
||||
}
|
||||
|
||||
// -------------------------------------------
|
||||
|
||||
private:
|
||||
|
||||
stack_based_memory_block<sizeof(bf_null_type)> bf_memory;
|
||||
|
||||
void destroy_bf_memory (
|
||||
)
|
||||
{
|
||||
// Honestly, this probably doesn't even do anything but I'm putting
|
||||
// it here just for good measure.
|
||||
bf()->~bound_function_helper_base_base();
|
||||
}
|
||||
|
||||
bfp1_helpers::bound_function_helper_base_base* bf ()
|
||||
{ return static_cast<bfp1_helpers::bound_function_helper_base_base*>(bf_memory.get()); }
|
||||
|
||||
const bfp1_helpers::bound_function_helper_base_base* bf () const
|
||||
{ return static_cast<const bfp1_helpers::bound_function_helper_base_base*>(bf_memory.get()); }
|
||||
|
||||
};
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
inline void swap (
|
||||
bound_function_pointer& a,
|
||||
bound_function_pointer& b
|
||||
) { a.swap(b); }
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
}
|
||||
|
||||
#endif // DLIB_BOUND_FUNCTION_POINTER_KERNEl_1_
|
||||
|
||||
@@ -0,0 +1,456 @@
|
||||
// Copyright (C) 2008 Davis E. King (davis@dlib.net)
|
||||
// License: Boost Software License See LICENSE.txt for the full license.
|
||||
#undef DLIB_BOUND_FUNCTION_POINTER_KERNEl_ABSTRACT_
|
||||
#ifdef DLIB_BOUND_FUNCTION_POINTER_KERNEl_ABSTRACT_
|
||||
|
||||
namespace dlib
|
||||
{
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
class bound_function_pointer
|
||||
{
|
||||
/*!
|
||||
INITIAL VALUE
|
||||
is_set() == false
|
||||
|
||||
WHAT THIS OBJECT REPRESENTS
|
||||
This object represents a function with all its arguments bound to
|
||||
specific objects. For example:
|
||||
|
||||
void test(int& var) { var = var+1; }
|
||||
|
||||
bound_function_pointer funct;
|
||||
|
||||
int a = 4;
|
||||
funct.set(test,a); // bind the variable a to the first argument of the test() function
|
||||
|
||||
// at this point a == 4
|
||||
funct();
|
||||
// after funct() is called a == 5
|
||||
!*/
|
||||
|
||||
public:
|
||||
|
||||
bound_function_pointer (
|
||||
);
|
||||
/*!
|
||||
ensures
|
||||
- #*this is properly initialized
|
||||
!*/
|
||||
|
||||
bound_function_pointer(
|
||||
const bound_function_pointer& item
|
||||
);
|
||||
/*!
|
||||
ensures
|
||||
- *this == item
|
||||
!*/
|
||||
|
||||
~bound_function_pointer (
|
||||
);
|
||||
/*!
|
||||
ensures
|
||||
- any resources associated with *this have been released
|
||||
!*/
|
||||
|
||||
bound_function_pointer& operator=(
|
||||
const bound_function_pointer& item
|
||||
);
|
||||
/*!
|
||||
ensures
|
||||
- *this == item
|
||||
!*/
|
||||
|
||||
void clear(
|
||||
);
|
||||
/*!
|
||||
ensures
|
||||
- #*this has its initial value
|
||||
!*/
|
||||
|
||||
bool is_set (
|
||||
) const;
|
||||
/*!
|
||||
ensures
|
||||
- if (this->set() has been called) then
|
||||
- returns true
|
||||
- else
|
||||
- returns false
|
||||
!*/
|
||||
|
||||
operator some_undefined_pointer_type (
|
||||
) const;
|
||||
/*!
|
||||
ensures
|
||||
- if (is_set()) then
|
||||
- returns a non 0 value
|
||||
- else
|
||||
- returns a 0 value
|
||||
!*/
|
||||
|
||||
bool operator! (
|
||||
) const;
|
||||
/*!
|
||||
ensures
|
||||
- returns !is_set()
|
||||
!*/
|
||||
|
||||
void operator () (
|
||||
) const;
|
||||
/*!
|
||||
requires
|
||||
- is_set() == true
|
||||
ensures
|
||||
- calls the bound function on the object(s) specified by the last
|
||||
call to this->set()
|
||||
throws
|
||||
- any exception thrown by the function specified by
|
||||
the previous call to this->set().
|
||||
If any of these exceptions are thrown then the call to this
|
||||
function will have no effect on *this.
|
||||
!*/
|
||||
|
||||
void swap (
|
||||
bound_function_pointer& item
|
||||
);
|
||||
/*!
|
||||
ensures
|
||||
- swaps *this and item
|
||||
!*/
|
||||
|
||||
// ----------------------
|
||||
|
||||
template <typename F>
|
||||
void set (
|
||||
F& function_object
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- function_object() is a valid expression
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call function_object()
|
||||
(This seems pointless but it is a useful base case)
|
||||
!*/
|
||||
|
||||
template < typename T>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)()
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid member function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)()
|
||||
!*/
|
||||
|
||||
template < typename T>
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)()const
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid bound function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)()
|
||||
!*/
|
||||
|
||||
void set (
|
||||
void (*funct)()
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid function pointer
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call funct()
|
||||
!*/
|
||||
|
||||
// ----------------------
|
||||
|
||||
template <typename F, typename A1 >
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- function_object(arg1) is a valid expression
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call function_object(arg1)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1 >
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1),
|
||||
A1& arg1
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid member function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1 >
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1)const,
|
||||
A1& arg1
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid bound function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1)
|
||||
!*/
|
||||
|
||||
template <typename T1, typename A1>
|
||||
void set (
|
||||
void (*funct)(T1),
|
||||
A1& arg1
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid function pointer
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call funct(arg1)
|
||||
!*/
|
||||
|
||||
// ----------------------
|
||||
template <typename F, typename A1, typename A2 >
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- function_object(arg1,arg2) is a valid expression
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call function_object(arg1,arg2)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1,
|
||||
typename T2, typename A2>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1,T2),
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid member function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1,arg2)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1,
|
||||
typename T2, typename A2>
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1,T2)const,
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid bound function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1,arg2)
|
||||
!*/
|
||||
|
||||
template <typename T1, typename A1,
|
||||
typename T2, typename A2>
|
||||
void set (
|
||||
void (*funct)(T1,T2),
|
||||
A1& arg1,
|
||||
A2& arg2
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid function pointer
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call funct(arg1,arg2)
|
||||
!*/
|
||||
|
||||
// ----------------------
|
||||
|
||||
template <typename F, typename A1, typename A2, typename A3 >
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- function_object(arg1,arg2,arg3) is a valid expression
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call function_object(arg1,arg2,arg3)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1,T2,T3),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid member function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1,arg2,arg3)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3>
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1,T2,T3)const,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid bound function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1,arg2,arg3)
|
||||
!*/
|
||||
|
||||
template <typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3>
|
||||
void set (
|
||||
void (*funct)(T1,T2,T3),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid function pointer
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call funct(arg1,arg2,arg3)
|
||||
!*/
|
||||
|
||||
// ----------------------
|
||||
|
||||
template <typename F, typename A1, typename A2, typename A3, typename A4>
|
||||
void set (
|
||||
F& function_object,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- function_object(arg1,arg2,arg3,arg4) is a valid expression
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call function_object(arg1,arg2,arg3,arg4)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3,
|
||||
typename T4, typename A4>
|
||||
void set (
|
||||
T& object,
|
||||
void (T::*funct)(T1,T2,T3,T4),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid member function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1,arg2,arg3,arg4)
|
||||
!*/
|
||||
|
||||
template < typename T, typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3,
|
||||
typename T4, typename A4>
|
||||
void set (
|
||||
const T& object,
|
||||
void (T::*funct)(T1,T2,T3,T4)const,
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid bound function pointer for class T
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call (object.*funct)(arg1,arg2,arg3,arg4)
|
||||
!*/
|
||||
|
||||
template <typename T1, typename A1,
|
||||
typename T2, typename A2,
|
||||
typename T3, typename A3,
|
||||
typename T4, typename A4>
|
||||
void set (
|
||||
void (*funct)(T1,T2,T3,T4),
|
||||
A1& arg1,
|
||||
A2& arg2,
|
||||
A3& arg3,
|
||||
A4& arg4
|
||||
);
|
||||
/*!
|
||||
requires
|
||||
- funct == a valid function pointer
|
||||
ensures
|
||||
- #is_set() == true
|
||||
- calls to this->operator() will call funct(arg1,arg2,arg3,arg4)
|
||||
!*/
|
||||
|
||||
};
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
inline void swap (
|
||||
bound_function_pointer& a,
|
||||
bound_function_pointer& b
|
||||
) { a.swap(b); }
|
||||
/*!
|
||||
provides a global swap function
|
||||
!*/
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
}
|
||||
|
||||
#endif // DLIB_BOUND_FUNCTION_POINTER_KERNEl_ABSTRACT_
|
||||
|
||||
Reference in New Issue
Block a user