implement an duplicate-value filtering iterator
This commit is contained in:
parent
0081b36793
commit
ff2113e61f
3 changed files with 81 additions and 0 deletions
|
|
@ -354,6 +354,37 @@ namespace lib {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper: predicate returning \c true
|
||||||
|
* whenever the argument value changes
|
||||||
|
* during a sequence of invocations.
|
||||||
|
*/
|
||||||
|
template<typename VAL>
|
||||||
|
class SkipRepetition
|
||||||
|
{
|
||||||
|
typedef wrapper::ItemWrapper<VAL> Item;
|
||||||
|
|
||||||
|
Item prev_;
|
||||||
|
|
||||||
|
public:
|
||||||
|
bool
|
||||||
|
operator() (VAL const& elm)
|
||||||
|
{
|
||||||
|
if (prev_ &&
|
||||||
|
(*prev_ == elm))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// element differs from predecessor
|
||||||
|
prev_ = elm;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
typedef bool result_type;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -509,6 +540,18 @@ namespace lib {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/** filters away repeated values
|
||||||
|
* emitted by source iterator */
|
||||||
|
template<class IT>
|
||||||
|
FilterIter<IT>
|
||||||
|
filterRepetitions (IT const& source)
|
||||||
|
{
|
||||||
|
typedef typename IT::value_type Val;
|
||||||
|
return filterIterator(source, SkipRepetition<Val>() );
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
} // namespace lib
|
} // namespace lib
|
||||||
|
|
|
||||||
|
|
@ -173,6 +173,7 @@ namespace wrapper {
|
||||||
/* == copy and assignment == */
|
/* == copy and assignment == */
|
||||||
|
|
||||||
ItemWrapper (ItemWrapper const& ref)
|
ItemWrapper (ItemWrapper const& ref)
|
||||||
|
: created_(false)
|
||||||
{
|
{
|
||||||
if (ref.isValid())
|
if (ref.isValid())
|
||||||
build (*ref);
|
build (*ref);
|
||||||
|
|
|
||||||
|
|
@ -30,6 +30,7 @@
|
||||||
|
|
||||||
#include <boost/lexical_cast.hpp>
|
#include <boost/lexical_cast.hpp>
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
#include <cstdlib>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -44,6 +45,7 @@ namespace test{
|
||||||
using std::vector;
|
using std::vector;
|
||||||
using std::cout;
|
using std::cout;
|
||||||
using std::endl;
|
using std::endl;
|
||||||
|
using std::rand;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -105,6 +107,7 @@ namespace test{
|
||||||
Iter ii (source.begin());
|
Iter ii (source.begin());
|
||||||
++++++ii;
|
++++++ii;
|
||||||
buildFilterIterator (ii);
|
buildFilterIterator (ii);
|
||||||
|
verify_filterRepetitions();
|
||||||
|
|
||||||
buildTransformingIterator (source.begin());
|
buildTransformingIterator (source.begin());
|
||||||
}
|
}
|
||||||
|
|
@ -147,6 +150,40 @@ namespace test{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/** @test verify the helper to filter duplicate elements
|
||||||
|
* emitted by an source iterator. This test creates
|
||||||
|
* a sequence of numbers with random repetitions.
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
verify_filterRepetitions ()
|
||||||
|
{
|
||||||
|
vector<uint> numberz;
|
||||||
|
for (uint i=0; i<NUM_ELMS; ++i)
|
||||||
|
{
|
||||||
|
uint n = 1 + rand() % 100;
|
||||||
|
do numberz.push_back(i);
|
||||||
|
while (--n);
|
||||||
|
}
|
||||||
|
ASSERT (NUM_ELMS < numberz.size(), "no repetition in test data??");
|
||||||
|
|
||||||
|
typedef vector<uint>::iterator SrcIter;
|
||||||
|
typedef RangeIter<SrcIter> SeqIter;
|
||||||
|
typedef FilterIter<SeqIter> FilteredSeq;
|
||||||
|
|
||||||
|
SeqIter completeSequence (numberz.begin(), numberz.end());
|
||||||
|
FilteredSeq filtered = filterRepetitions (completeSequence);
|
||||||
|
|
||||||
|
uint num=0;
|
||||||
|
for (; num<NUM_ELMS && !isnil(filtered);
|
||||||
|
++num,
|
||||||
|
++filtered
|
||||||
|
)
|
||||||
|
ASSERT (num == *filtered);
|
||||||
|
|
||||||
|
ASSERT (num == NUM_ELMS && isnil(filtered));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static ulong addTwo (int i) { return i+2; }
|
static ulong addTwo (int i) { return i+2; }
|
||||||
static int negate (int i) { return -i; }
|
static int negate (int i) { return -i; }
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue