#include <vector>
using namespace std;
template< typename TBufferTypeFront, typename TBufferTypeBack = TBufferTypeFront>
class FrontBackBuffer {
public:
template <typename T>
struct MyRefTypes {
typedef const T & Con;
typedef T& Ref;
typedef const T& CRef;
static Ref getRef(T& v) {
return v;
}
};
//Specialization for Reference
template <typename T>
struct MyRefTypes<T&> {
typedef T & Con;
typedef T& Ref;
typedef const T& CRef;
static inline Ref getRef(T& v) {
return v;
}
};
//Specialization for const Reference
template <typename T>
struct MyRefTypes<const T&> {
typedef const T & Con;
typedef const T& Ref;
typedef const T& CRef;
static inline Ref getRef(const T& v) {
return v;
}
};
//Specialization for const
template <typename T>
struct MyRefTypes<const T> {
typedef const T & Con;
typedef const T& Ref;
typedef const T& CRef;
static inline Ref getRef(const T& v) {
return v;
}
};
//Specialization for pointers
template <typename T>
struct MyRefTypes<T*> {
typedef T* Con;
typedef T& Ref;
typedef T* const CRef; //! note this is a pointer....
static inline Ref getRef(T* v) {
return *v;
}
};
//Specialization for const pointers
template <typename T>
struct MyRefTypes<const T*> {
typedef const T* Con;
typedef const T& Ref;
typedef const T* const CRef; //! note this is a pointer....
static inline Ref getRef(const T* v) {
return *v;
}
};
typedef typename MyRefTypes<TBufferTypeFront>::Ref TBufferTypeFrontRef;
typedef typename MyRefTypes<TBufferTypeFront>::CRef TBufferTypeFrontCRef;
typedef typename MyRefTypes<TBufferTypeFront>::Con TBufferTypeFrontCon;
typedef typename MyRefTypes<TBufferTypeBack >::Ref TBufferTypeBackRef;
typedef typename MyRefTypes<TBufferTypeBack >::CRef TBufferTypeBackCRef;
typedef typename MyRefTypes<TBufferTypeBack >::Con TBufferTypeBackCon;
// Remove reference because const T & yields with T = int& -> int&
explicit FrontBackBuffer(
TBufferTypeFrontCon m_front,
TBufferTypeBackCon m_back):
m_Front(m_front),
m_Back(m_back)
{
};
~FrontBackBuffer()
{};
TBufferTypeFrontRef getFront() {
return MyRefTypes<TBufferTypeFront>::getRef(m_Front);
}
TBufferTypeBackRef getBack() {
return MyRefTypes<TBufferTypeBack>::getRef(m_Back);
}
private:
TBufferTypeFront m_Front; ///< The front buffer
TBufferTypeBack m_Back; ///< The back buffer
};
typedef std::vector<float> GAGAType ;
int main() {
int aa = 7;
FrontBackBuffer<int&, double> a(aa,7);
//a.getFront() = 4 //COmpile error! OK!;
a.getBack() = 4;
const int r = 7;
FrontBackBuffer<const int&, std::vector<int> > a1(r, std::vector<int>(7));
//a.getFront() = 4 //COmpile error! OK!;
a1.getBack()[0] = 4;
int bb;
GAGAType bbb;
FrontBackBuffer< int*, GAGAType * > b(&bb, &bbb);
b.getBack().push_back(0);
b.getFront() = int (4);
}