From 60301f7523684cdcbc140052a86909579300d2a3 Mon Sep 17 00:00:00 2001 From: Ichthyostega Date: Thu, 30 Nov 2017 21:02:36 +0100 Subject: [PATCH] Library: need an augmented version of the iterator type rebinding helper yet another quick-n-dirty hack turned into an useful everyday helper... but at least I need it to be symmetric in and universally applyable --- src/lib/iter-type-binding.hpp | 15 +- src/lib/meta/value-type-binding.hpp | 117 ++++++++++++ tests/library/meta/type-display-test.cpp | 10 +- .../library/meta/value-type-binding-test.cpp | 176 ++++++++++++++++++ 4 files changed, 308 insertions(+), 10 deletions(-) create mode 100644 src/lib/meta/value-type-binding.hpp create mode 100644 tests/library/meta/value-type-binding-test.cpp diff --git a/src/lib/iter-type-binding.hpp b/src/lib/iter-type-binding.hpp index fa9e85c65..12513dc9d 100644 --- a/src/lib/iter-type-binding.hpp +++ b/src/lib/iter-type-binding.hpp @@ -29,6 +29,7 @@ ** iterators or custom containers, explicit specialisations ** might be injected prior to instantiating the Iterator adapter ** template. + ** @deprecated rework into a generic meta helper 11/2017 ** ** @see iter-adapter.hpp ** @see scope-path.hpp usage example (explicit specialisation) @@ -59,7 +60,7 @@ namespace iter { * @note client code might define specialisations * to handle tricky situations (like const_reverse_iter) */ - template + template struct TypeBinding { typedef typename TY::pointer pointer; @@ -115,6 +116,18 @@ namespace iter { typedef size_t* pointer; }; + /** + * specialisation for classes providing + * STL style type binding definitions themselves + */ + template + struct TypeBinding + { + typedef typename TY::pointer pointer; + typedef typename TY::reference reference; + typedef typename TY::value_type value_type; + }; + }} // namespace lib diff --git a/src/lib/meta/value-type-binding.hpp b/src/lib/meta/value-type-binding.hpp new file mode 100644 index 000000000..a5ff19662 --- /dev/null +++ b/src/lib/meta/value-type-binding.hpp @@ -0,0 +1,117 @@ +/* + VALUE-TYPE-BINDING.hpp - control type variations for IterAdapter + + Copyright (C) Lumiera.org + 2010, Hermann Vosseler + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License as + published by the Free Software Foundation; either version 2 of + the License, or (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +*/ + +/** @file value-type-binding.hpp + ** Type re-binding helper template for IterAdapter and friends. + ** This header defines a trait template which is used by the Iterator + ** adapters to figure out the value-, pointer- and reference types + ** when wrapping iterators or containers. For extending the use of + ** Iterator adapters and Iter-tools to situations involving const + ** iterators or custom containers, explicit specialisations + ** might be injected prior to instantiating the Iterator adapter + ** template. + ** + ** @see iter-adapter.hpp + ** @see scope-path.hpp usage example (explicit specialisation) + */ + + +#ifndef LIB_META_VALUE_TYPE_BINDING_H +#define LIB_META_VALUE_TYPE_BINDING_H + + +#include "lib/error.hpp" + + + +namespace std { + template + class shared_ptr; +} + +namespace lib { +namespace meta { + + /** + * Type re-binding helper template for creating nested typedefs + * for use by IterAdapter or similar "Lumiera Forward Iterators". + * This trait provides a value-, reference- and pointer type, + * similar to what the STL does. + * @note client code might define specialisations + * to handle tricky situations (like const_reverse_iter) + */ + template + struct TypeBinding + { + typedef TY value_type; + typedef TY& reference; + typedef TY* pointer; + }; + + template + struct TypeBinding + { + typedef TY value_type; + typedef TY& reference; + typedef TY* pointer; + }; + + template + struct TypeBinding + { + typedef TY value_type; + typedef const TY& reference; + typedef const TY* pointer; + }; + + template + struct TypeBinding + { + typedef TY value_type; + typedef TY& reference; + typedef TY* pointer; + }; + + template + struct TypeBinding + { + typedef TY value_type; + typedef const TY& reference; + typedef const TY* pointer; + }; + + /** + * specialisation for classes providing + * STL style type binding definitions themselves + */ + template + struct TypeBinding + { + typedef typename TY::pointer pointer; + typedef typename TY::reference reference; + typedef typename TY::value_type value_type; + }; + + + +}} // namespace lib::meta +#endif /*LIB_META_VALUE_TYPE_BINDING_H*/ diff --git a/tests/library/meta/type-display-test.cpp b/tests/library/meta/type-display-test.cpp index ca201c475..8a6752cf4 100644 --- a/tests/library/meta/type-display-test.cpp +++ b/tests/library/meta/type-display-test.cpp @@ -26,21 +26,13 @@ #include "lib/test/run.hpp" - -//#include "lib/p.hpp" -//#include "lib/diff/gen-node.hpp" - #include "lib/meta/util.hpp" +#include "lib/format-cout.hpp" -#include //////////TODO #include -//using lib::P; -//using lib::diff::GenNode; using std::string; -using std::cout; /////////////TODO -using std::endl; /////////////TODO namespace lib { diff --git a/tests/library/meta/value-type-binding-test.cpp b/tests/library/meta/value-type-binding-test.cpp new file mode 100644 index 000000000..5d6ebd1b5 --- /dev/null +++ b/tests/library/meta/value-type-binding-test.cpp @@ -0,0 +1,176 @@ +/* + ValueTypeBinding(Test) - human readable simplified display of C++ types + + Copyright (C) Lumiera.org + 2017, Hermann Vosseler + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License as + published by the Free Software Foundation; either version 2 of + the License, or (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +* *****************************************************/ + +/** @file type-display-test.cpp + ** unit test \ref ValueTypeBinding_test + */ + + +#include "lib/test/run.hpp" +#include "lib/meta/value-type-binding.hpp" +#include "lib/format-cout.hpp" +#include "lib/meta/util.hpp" ///////TODO RLY? + +#include +#include + + +using std::string;/////////////TODO + + +namespace lib { +namespace meta{ +namespace test{ + + namespace { // test fixture + + template + struct Outer + { + struct Inner + { + T val; + }; + + typedef T value_type; + typedef Inner const& reference; + typedef std::shared_ptr pointer; + }; + + struct Space { }; + using Join = ulong; + + template + inline string + showType() + { + return humanReadableTypeID (typeid(X).name()); + } + + }//(end)fixture + + + + + /**********************************************************************************//** + * @test verify result type rebinding for containers, iterators values and references. + * When augmenting, combining or decorating generic entities, there is often the need + * to find out about the `value_type`, a `reference` or `pointer` to such a value. + * Many STL compliant containers and iterators provide suitably nested type definitions + * to indicate those types. The meta::TypeBinding helper allows to pick up such + * definitions, and additionally it levels and unifies access for various combinations + * of primitive types, references and pointers. The purpose of this test is to verify + * and document this behaviour. + * + * @see value-type-binding.hpp + * @see lib::RangeIter + * @see lib::TreeExplorer::transform() + */ + class ValueTypeBinding_test + : public Test + { + void + run (Arg) + { + using OuterSpace = Outer; + + cout << showType() <() <() <::value_type>() <::reference>() <::pointer>() <>::value_type>() <>::reference>() <>::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <::value_type>() <::reference>() <::pointer>() <