From d98d1d057f19bdf3d8846b049da2e6d56e7c49ea Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20M=C3=B6ller?= Date: Thu, 23 Jun 2011 13:09:49 +0000 Subject: [PATCH] Object: Made implicit conversion from optional safer Overload: Added generalised overloads and tests --- .gitattributes | 2 + STL_Extension/include/CGAL/Object.h | 6 +-- STL_Extension/include/CGAL/Overload.h | 48 +++++++++++++++++++ .../test/STL_Extension/test_Overload.cpp | 43 +++++++++++++++++ 4 files changed, 96 insertions(+), 3 deletions(-) create mode 100644 STL_Extension/include/CGAL/Overload.h create mode 100644 STL_Extension/test/STL_Extension/test_Overload.cpp diff --git a/.gitattributes b/.gitattributes index ca70da0a47d..64ca2ffa2a9 100644 --- a/.gitattributes +++ b/.gitattributes @@ -3187,7 +3187,9 @@ Ridges_3/examples/Ridges_3/skip_vcproj_auto_generation -text Ridges_3/test/Ridges_3/data/ellipsoid.off -text svneol=unset#application/octet-stream Robustness/demo/Robustness/help/index.html svneol=native#text/html STL_Extension/doc_tex/STL_Extension/plusplus.png -text +STL_Extension/include/CGAL/Overload.h -text STL_Extension/test/STL_Extension/test_Object.cpp -text +STL_Extension/test/STL_Extension/test_Overload.cpp -text STL_Extension/test/STL_Extension/test_Uncertain.cpp -text STL_Extension/test/STL_Extension/test_type_traits.cpp -text Scripts/developer_scripts/autotest_cgal -text diff --git a/STL_Extension/include/CGAL/Object.h b/STL_Extension/include/CGAL/Object.h index 7cddf7ec320..ecad553ba40 100644 --- a/STL_Extension/include/CGAL/Object.h +++ b/STL_Extension/include/CGAL/Object.h @@ -107,9 +107,9 @@ class Object } #endif - // implicit constructor from boost::variant - template - Object(const T& t) { + // implicit constructor from optionals containing variants + template + Object(const boost::optional& t) { // we cannot invoke another ctor from here, so we have to behave // like the copy ctor of our base if(t) { diff --git a/STL_Extension/include/CGAL/Overload.h b/STL_Extension/include/CGAL/Overload.h new file mode 100644 index 00000000000..d99ee0aebb1 --- /dev/null +++ b/STL_Extension/include/CGAL/Overload.h @@ -0,0 +1,48 @@ +#ifndef _COMPOSITE_VISITOR_H_ +#define _COMPOSITE_VISITOR_H_ + +#include + +#if !defined(CGAL_CFG_NO_CPP0X_VARIADIC_TEMPLATES) && !defined(CGAL_CFG_NO_CPP0X_TUPLE) + +#include + +namespace CGAL { + +template +struct overload_helper : public overload_helper { + typedef typename std::tuple_element::type inner_type; + + typename inner_type::result_type operator()(typename inner_type::argument_type x) { + return std::get(static_cast(this)->t)(x); } + + using overload_helper::operator(); +}; + +template +struct overload_helper { + typedef typename std::tuple_element<0 ,T>::type inner_type; + + typename inner_type::result_type operator()(typename inner_type::argument_type x) { + return std::get<0>(static_cast(this)->t)(x); } +}; + +template +struct overload : public overload_helper::value, overload > +{ + // + typedef typename std::tuple_element<0, T>::type::result_type result_type; + + T t; + overload(T&& t) : t(t) {} + overload(const T& t) : t(t) {} +}; + +template +overload make_overload(T&& t) { return overload(t); } + +} // namespace CGAL +#endif // !defined(CGAL_CFG_NO_CPP0X_VARIADIC_TEMPLATES) && !defined(CGAL_CFG_NO_CPP0X_TUPLE) + +#endif /* _COMPOSITE_VISITOR_H_ */ + diff --git a/STL_Extension/test/STL_Extension/test_Overload.cpp b/STL_Extension/test/STL_Extension/test_Overload.cpp new file mode 100644 index 00000000000..8d3cbef8009 --- /dev/null +++ b/STL_Extension/test/STL_Extension/test_Overload.cpp @@ -0,0 +1,43 @@ +#include + +#if !defined(CGAL_CFG_NO_CPP0X_VARIADIC_TEMPLATES) && !defined(CGAL_CFG_NO_CPP0X_TUPLE) + +#include +#include +#include +#include +#include +#include + + +void test_overload() { + using namespace CGAL; + using std::function; + + // basic overload checking + auto o = make_overload(std::make_tuple( + function([](int) { return 1; }), + function([](char) { return 2; }), + function([](double) { return 3; }))); + + CGAL_assertion(o(1) == 1); + CGAL_assertion(o('a') == 2); + CGAL_assertion(o(2.0) == 3); + + // check for variants + boost::variant v1 = 1; + boost::variant v2 = 'a'; + boost::variant v3 = 2.0; + + CGAL_assertion(boost::apply_visitor(o, v1) == 1); + CGAL_assertion(boost::apply_visitor(o, v2) == 2); + CGAL_assertion(boost::apply_visitor(o, v3) == 3); +} + +#endif + +int main() { +#if !defined(CGAL_CFG_NO_CPP0X_VARIADIC_TEMPLATES) && !defined(CGAL_CFG_NO_CPP0X_TUPLE) + test_overload(); +#endif +}