-
Jan Trávníček authoredJan Trávníček authored
Code owners
Assign users and groups as approvers for specific file changes. Learn more.
ValueProvider.hpp 2.90 KiB
/*
* ValueProvider.hpp
*
* Created on: 11. 7. 2017
* Author: Jan Travnicek
*/
#ifndef _VALUE_PROVIDER_HPP_
#define _VALUE_PROVIDER_HPP_
#include <exception>
#include <alib/utility>
namespace abstraction {
template < class Type >
class ValueProvider {
protected:
virtual bool isConst ( ) const = 0;
virtual bool isLvalueRef ( ) const = 0;
virtual bool isRvalueRef ( ) const = 0;
virtual Type & getData ( ) const = 0;
public:
Type getValue ( bool move ) const {
if constexpr ( std::is_copy_constructible_v < Type > && std::is_move_constructible_v < Type > ) {
if ( ! isConst ( ) && move )
return std::move ( getData ( ) );
else
return getData ( );
} else if constexpr ( std::is_copy_constructible_v < Type > && ! std::is_move_constructible_v < Type > ) {
if ( ! isConst ( ) && move )
throw std::domain_error ( "Value not move constructible" );
else
return getData ( );
} else if constexpr ( ! std::is_copy_constructible_v < Type > && std::is_move_constructible_v < Type > ) {
if ( ! isConst ( ) && move )
return std::move ( getData ( ) );
else
throw std::domain_error ( "Value not copy constructible" );
} else { // ! std::is_copy_constructible_v < Type > && ! std::is_move_constructible_v < Type >
if ( ! isConst ( ) && move )
throw std::domain_error ( "Value not move constructible" );
else
throw std::domain_error ( "Value not copy constructible" );
}
}
};
template < class Type >
class ValueProvider < Type & > {
protected:
virtual bool isConst ( ) const = 0;
virtual bool isLvalueRef ( ) const = 0;
virtual bool isRvalueRef ( ) const = 0;
virtual Type & getData ( ) const = 0;
public:
Type & getValue ( bool ) const {
return getData ( );
}
};
template < class Type >
class ValueProvider < const Type & > {
protected:
virtual bool isConst ( ) const = 0;
virtual bool isLvalueRef ( ) const = 0;
virtual bool isRvalueRef ( ) const = 0;
virtual const Type & getConstData ( ) const = 0;
public:
const Type & getValue ( bool ) const {
return getConstData ( );
}
};
template < class Type >
class ValueProvider < Type && > {
protected:
virtual bool isConst ( ) const = 0;
virtual bool isLvalueRef ( ) const = 0;
virtual bool isRvalueRef ( ) const = 0;
virtual Type & getData ( ) const = 0;
public:
Type && getValue ( bool move ) const {
if ( move )
return std::move ( getData ( ) );
else
throw std::domain_error ( "Value not copy constructible" );
}
};
template < class Type >
class ValueProvider < const Type && > {
protected:
virtual bool isConst ( ) const = 0;
virtual bool isLvalueRef ( ) const = 0;
virtual bool isRvalueRef ( ) const = 0;
virtual const Type & getConstData ( ) const = 0;
public:
const Type && getValue ( bool move ) const {
if ( move )
return std::move ( getConstData ( ) );
else
throw std::domain_error ( "Value not copy constructible" );
}
};
} /* namespace abstraction */
#endif /* _VALUE_PROVIDER_HPP_ */