TreeExplorer: allow to call through an IterSource based API for child-expansion

...which basically allows us to return any suitable implementation
for the child iterator, even to switch the concrete iteration on each level.
We need this flexibility when implementing navigation through a concrete UI
This commit is contained in:
Fischlurch 2017-12-24 03:28:40 +01:00
parent f05b3f56c0
commit d653937465
3 changed files with 81 additions and 49 deletions

View file

@ -303,6 +303,15 @@ namespace lib {
IterSourceIter (ISO* heap_allocated_IterSource)
: ISO::iterator{ISO::build (heap_allocated_IterSource)}
{ }
using Source = ISO;
Source&
source()
{
REQUIRE (ISO::iterator::isValid());
return static_cast<ISO&> (*ISO::iterator::source());
}
};
}//(End) namespace iter_explorer : basic iterator wrappers
@ -319,6 +328,7 @@ namespace lib {
using meta::_Fun;
using std::__and_;
using std::__not_;
using std::is_base_of;
using std::is_convertible;
using std::remove_reference_t;
using meta::can_IterForEach;
@ -401,14 +411,14 @@ namespace lib {
};
template<class ISO>
struct _DecoratorTraits<ISO*, enable_if<std::is_base_of<IterSource<typename ISO::value_type>, ISO>>>
struct _DecoratorTraits<ISO*, enable_if<is_base_of<IterSource<typename ISO::value_type>, ISO>>>
{
using SrcIter = iter_explorer::IterSourceIter<ISO>;
using SrcVal = typename ISO::value_type;
};
template<class ISO>
struct _DecoratorTraits<ISO&, enable_if<std::is_base_of<IterSource<typename ISO::value_type>, ISO>>>
struct _DecoratorTraits<ISO&, enable_if<is_base_of<IterSource<typename ISO::value_type>, ISO>>>
{
using SrcIter = iter_explorer::IterSourceIter<ISO>;
using SrcVal = typename ISO::value_type;
@ -491,6 +501,17 @@ namespace lib {
static auto build() { return [](auto& iter) { return *iter; }; }
};
/** adapt to a functor collaborating with an IterSource based iterator pipeline */
template<class IT>
struct ArgAccessor<IT, enable_if<__and_< is_base_of<IterSource<typename IT::value_type>, typename IT::Source>
, is_base_of<IterSource<typename IT::value_type>, remove_reference_t<Arg>>
> >>
{
using Source = typename IT::Source;
static auto build() { return [](auto& iter) -> Source& { return iter.source(); }; }
};
/** holder for the suitably adapted _expansion functor_ */
struct Functor

View file

@ -849,8 +849,17 @@ namespace test{
/** @test ability to wrap and handle IterSource based iteration
*
/** @test ability to wrap and handle IterSource based iteration.
* Contrary to the preceding test case, here the point is to _base the whole pipleine_
* on a data source accessible through the IterSource (VTable based) interface. The notable
* point with this technique is the ability to use some _extended sub interface of IterSource_
* and to rely on this interface to implement some functor bound into the TreeExplorer pipeline.
* Especially this allows to delegate the "child expansion" through such an interface and just
* return a compatible IterSource as result. This way, the opaque implementation gains total
* freedom regarding the concrete implementation of the "child series" iterator. In fact,
* it may even use a different implementation on each level or even on each individual call;
* only the result type and thus the base interface need to match.
*/
void
verify_IterSource()
@ -874,7 +883,7 @@ namespace test{
virtual PrivateSource*
expandChildren() const override
{
return new VerySpecivicIter{*wrappedIter() - 1};
return new VerySpecivicIter{*wrappedIter() - 2};
}
uint
@ -892,45 +901,44 @@ namespace test{
VerySpecivicIter vsit{4};
// attach to an IterSource living here in local scope...
auto ii = treeExplore(vsit);
VerySpecivicIter vsit{5};
// ...and build a child expansion on top, which calls through the PrivateSource-API
// Effectively this means we do not know the concrete type of the "expanded children" iterator,
// only that it adheres to the same IterSource sub-interface as used on the base iterator.
auto ii = treeExplore(vsit)
.expand ([](PrivateSource& source){ return source.expandChildren(); });
CHECK (not isnil (ii));
CHECK (5 == *ii);
CHECK (5 == vsit.currentVal());
++ii;
CHECK (4 == *ii);
CHECK (4 == vsit.currentVal());
CHECK (0 == ii.depth());
ii.expandChildren(); // note: calls through source's VTable to invoke VerySpecificIter::expandChildren()
CHECK (1 == ii.depth());
CHECK (2 == *ii);
++ii;
CHECK (1 == *ii);
CHECK (3 == vsit.currentVal());
CHECK (1 == ii.depth());
++ii;
CHECK (0 == ii.depth());
CHECK (3 == *ii);
CHECK (3 == vsit.currentVal());
#if false /////////////////////////////////////////////////////////////////////////////////////////////////////////////UNIMPLEMENTED :: TICKET #888
auto jj = ii.explore([](PrivateSource& source){ return source.expandChildren(); });
CHECK (3 == *jj);
CHECK (3 == vsit.currentVal());
CHECK (0 == jj.depth());
jj.expandChildren();
CHECK (1 == jj.depth());
CHECK (2 == *jj);
++jj;
CHECK (1 == *jj);
++ii;
CHECK (2 == *ii);
CHECK (2 == vsit.currentVal());
CHECK (1 == jj.depth());
++jj;
CHECK (0 == jj.depth());
CHECK (2 == *jj);
CHECK (2 == vsit.currentVal());
++jj;
CHECK (1 == *jj);
++ii;
CHECK (1 == *ii);
CHECK (1 == vsit.currentVal());
++jj;
CHECK (isnil (jj));
CHECK (0 == vsit.currentVal());
#endif /////////////////////////////////////////////////////////////////////////////////////////////////////////////UNIMPLEMENTED :: TICKET #888
++ii;
CHECK (isnil (ii));
}

View file

@ -5149,7 +5149,7 @@
<node CREATED="1512278456672" ID="ID_488770369" MODIFIED="1512278462388" TEXT="wird in jedem Schritt gestrippt"/>
</node>
</node>
<node COLOR="#338800" CREATED="1510941463562" ID="ID_845080696" MODIFIED="1513477667435" TEXT="TreeExplorer">
<node COLOR="#338800" CREATED="1510941463562" FOLDED="true" ID="ID_845080696" MODIFIED="1514082136259" TEXT="TreeExplorer">
<linktarget COLOR="#585e9d" DESTINATION="ID_845080696" ENDARROW="Default" ENDINCLINATION="-101;761;" ID="Arrow_ID_402051988" SOURCE="ID_1359727169" STARTARROW="None" STARTINCLINATION="208;5;"/>
<linktarget COLOR="#83dfc7" DESTINATION="ID_845080696" ENDARROW="Default" ENDINCLINATION="-1109;3887;" ID="Arrow_ID_1645152965" SOURCE="ID_30857289" STARTARROW="None" STARTINCLINATION="2051;-176;"/>
<linktarget COLOR="#406878" DESTINATION="ID_845080696" ENDARROW="Default" ENDINCLINATION="-88;-61;" ID="Arrow_ID_409690433" SOURCE="ID_1160853986" STARTARROW="None" STARTINCLINATION="-374;6;"/>
@ -5892,7 +5892,7 @@
</node>
</node>
</node>
<node COLOR="#338800" CREATED="1512363286920" ID="ID_1420123769" MODIFIED="1513990796074" TEXT="Zusammenspiel">
<node COLOR="#338800" CREATED="1512363286920" FOLDED="true" ID="ID_1420123769" MODIFIED="1514081201770" TEXT="Zusammenspiel">
<icon BUILTIN="button_ok"/>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1512844805995" ID="ID_927486947" MODIFIED="1512927037825" TEXT="single-val">
<icon BUILTIN="help"/>
@ -6364,17 +6364,17 @@
</node>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1513990803915" ID="ID_292438102" MODIFIED="1513990973201" TEXT="IterSource-Integration">
<node COLOR="#338800" CREATED="1513990803915" ID="ID_292438102" MODIFIED="1514081144696" TEXT="IterSource-Integration">
<linktarget COLOR="#659fa4" DESTINATION="ID_292438102" ENDARROW="Default" ENDINCLINATION="853;414;" ID="Arrow_ID_1802135668" SOURCE="ID_1529167083" STARTARROW="None" STARTINCLINATION="674;0;"/>
<icon BUILTIN="flag-yellow"/>
<icon BUILTIN="button_ok"/>
<node COLOR="#338800" CREATED="1513990840253" ID="ID_923982542" MODIFIED="1514050246345" TEXT="wrapper und Iterator bauen">
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1513990851580" ID="ID_1445466432" MODIFIED="1513990865914" TEXT="Traits erweitern">
<icon BUILTIN="flag-yellow"/>
<node COLOR="#338800" CREATED="1513990851580" ID="ID_1445466432" MODIFIED="1514081134408" TEXT="Traits erweitern">
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1513990858787" ID="ID_1444097417" MODIFIED="1513990866482" TEXT="Funktor erweitern">
<icon BUILTIN="flag-yellow"/>
<node COLOR="#338800" CREATED="1513990858787" ID="ID_1444097417" MODIFIED="1514081138141" TEXT="Funktor erweitern">
<icon BUILTIN="button_ok"/>
</node>
</node>
</node>
@ -6749,7 +6749,7 @@
</node>
</node>
</node>
<node COLOR="#338800" CREATED="1510941467586" ID="ID_381928532" MODIFIED="1513990811649" TEXT="TreeExplorer_test">
<node COLOR="#338800" CREATED="1510941467586" FOLDED="true" ID="ID_381928532" MODIFIED="1514081222409" TEXT="TreeExplorer_test">
<icon BUILTIN="button_ok"/>
<node COLOR="#338800" CREATED="1510969031378" ID="ID_1678287752" MODIFIED="1512927037810" TEXT="verify_wrappedIterator();">
<icon BUILTIN="button_ok"/>
@ -7065,13 +7065,16 @@
<node CREATED="1512789946314" ID="ID_1425696979" MODIFIED="1512789953964" TEXT="widerspricht dem Iteratoren-Konzept"/>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1513990814361" ID="ID_306902168" MODIFIED="1513990821537" TEXT="verify_IterSource()">
<icon BUILTIN="flag-yellow"/>
<node COLOR="#338800" CREATED="1513990814361" ID="ID_306902168" MODIFIED="1514081187635" TEXT="verify_IterSource()">
<icon BUILTIN="button_ok"/>
<node COLOR="#338800" CREATED="1513990873545" ID="ID_1789456983" MODIFIED="1514050256867" TEXT="einfache Iteration">
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1513990880600" ID="ID_1730629901" MODIFIED="1513990886456" TEXT="Iteration + Expansion">
<icon BUILTIN="flag-yellow"/>
<node COLOR="#338800" CREATED="1514081155455" ID="ID_1538736368" MODIFIED="1514081182820" TEXT="Iteration ohne storage management">
<icon BUILTIN="button_ok"/>
</node>
<node COLOR="#338800" CREATED="1513990880600" ID="ID_1730629901" MODIFIED="1514081152728" TEXT="Iteration + Expansion">
<icon BUILTIN="button_ok"/>
</node>
</node>
<node COLOR="#338800" CREATED="1510969031379" ID="ID_1327871737" MODIFIED="1512952095270" TEXT="verify_depthFirstExploration();">
@ -8130,9 +8133,9 @@
<node CREATED="1513988974179" ID="ID_900695722" MODIFIED="1513992358833" TEXT="Funktoren k&#xf6;nnen dieses Sub-Interface akzeptieren und liefern">
<icon BUILTIN="yes"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1513989030587" ID="ID_1529167083" MODIFIED="1513990973201" TEXT="TreeExplorer &#xfc;bernimmt / wrappt / packt aus">
<node COLOR="#338800" CREATED="1513989030587" ID="ID_1529167083" MODIFIED="1514082163308" TEXT="TreeExplorer &#xfc;bernimmt / wrappt / packt aus">
<arrowlink COLOR="#659fa4" DESTINATION="ID_292438102" ENDARROW="Default" ENDINCLINATION="853;414;" ID="Arrow_ID_1802135668" STARTARROW="None" STARTINCLINATION="674;0;"/>
<icon BUILTIN="flag-yellow"/>
<icon BUILTIN="button_ok"/>
</node>
</node>
</node>