How can I make this custom fmt formatter code cleaner? - c++

I want to write a custom formatter for simple structures inheriting from the existing formatters to access all their options. For example, I've written this for a rectangle:
#include <fmt/format.h>
template<typename T>
struct rect {
T x;
T y;
T width;
T height;
};
template <typename T>
struct fmt::formatter<rect<T>>: formatter<T> {
template <typename FormatContext>
auto format(rect<T> c, FormatContext& ctx) const {
auto out = ctx.out();
fmt::format_to(out, "[(");
out = formatter<T>::format(c.x, ctx);
fmt::format_to(out, ", ");
ctx.advance_to(out);
out= formatter<T>::format(c.y, ctx);
fmt::format_to(out, "), ");
ctx.advance_to(out);
out = formatter<T>::format(c.width, ctx);
fmt::format_to(out, " x ");
ctx.advance_to(out);
out = formatter<T>::format(c.height, ctx);
fmt::format_to(out, "]");
return out;
}
};
int main()
{
rect<double> f = {1.0, 2.3445, 3.14, 4};
fmt::print("{:.2f}\n", f);
rect<int> b = {1, 2, 3, 4};
fmt::print("{}\n", b);
return 0;
}
It works as expected, but the code inside the format() call seems a bit too convoluted. Q:
Is there a way of making it better, or at least cleaner?
Is format_to(...) the best option for adding those characters to the output?

Maybe you want like this. Note you have to implement parse and format methods both as per https://fmt.dev/latest/api.html#formatting-user-defined-types:
template < typename T >
struct fmt::formatter < rect < T >>: formatter < T > {
int floating_point_precision = 0;
constexpr auto parse(format_parse_context & ctx) -> decltype(ctx.begin()) {
auto it = ctx.begin(), end = ctx.end();
if (it != end && ( * it == '.')) it++;
if (it != end && ( * it >= '0' && * it <= '9')) {
floating_point_precision = * it - '0';
it++;
}
if (it != end && ( * it == 'f')) it++;
// Check if reached the end of the range:
if (it != end && * it != '}') throw format_error("invalid format");
// Return an iterator past the end of the parsed range:
return it;
}
template < typename FormatContext >
auto format(rect < T > c, FormatContext & ctx) const {
auto out = ctx.out();
if (floating_point_precision == 0)
fmt::format_to(out, "[({}, {}), {} x {}]", c.x, c.y, c.width, c.height);
else {
std::stringstream ss;
ss << "[({:." << floating_point_precision << "f}, {:." << floating_point_precision << "f}), "
"{:." << floating_point_precision << "f} x {:." << floating_point_precision << "f}]";
fmt::format_to(out, ss.str(), c.x, c.y, c.width, c.height);
}
return out;
}
};

You can make the code a bit cleaner as follows:
Move the element formatting logic into a separate function/lambda and reuse it in 4 places.
Remove redundant namespace qualification since the formatter is defined in the fmt namespace.
template <typename T>
struct fmt::formatter<rect<T>>: formatter<T> {
template <typename FormatContext>
auto format(rect<T> c, FormatContext& ctx) const {
auto out = ctx.out();
auto format_element = [&](const T& value) {
ctx.advance_to(out);
out = formatter<T>::format(value, ctx);
};
out = format_to(out, "[(");
format_element(c.x);
out = format_to(out, ", ");
format_element(c.y);
out = format_to(out, "), ");
format_element(c.width);
out = format_to(out, " x ");
format_element(c.height);
return format_to(out, "]");
}
};
Full example: https://godbolt.org/z/b8E88d3dG.
format_to is a reasonable way to output literal text but you could use std:copy instead.

Related

C++ {fmt} library, user-defined types with nested replacement fields?

I am trying to add {fmt} into my project, and all is going well, except I hit a little snag when trying to add a user-defined type for my simple Vec2 class.
struct Vec2 { float x; float y; };
What I would like is to be able to use the same format flags/arguments as the basic built-in float type, but have it duplicated to both the x and y members of the vec2, with parentheses around it.
For example, with just a float:
fmt::format("Hello '{0:<8.4f}' World!", 1.234567);
// results in "Hello '1.2346 ' World!"
With my vec2 class:
Vec2 v {1.2345678, 2.3456789};
fmt::format("Hello '{0:<8}' World!", v);
// results in "Hello (1.2346 , 2.3457 )' World!"
But my naïve method of copying over the replacement field contents doesn't work when we try to use nested replacement fields.
Eg with a float:
fmt::format("Hello '{0:<{1}.4f}' World!", 1.234567, 8);
// results in "Hello '1.2346 ' World!"
But trying with my Vec2 type...
Vec2 v {1.2345678, 2.3456789};
fmt::format("Hello '{0:<{1}.4f}' World!", v, 8);
// throws format_error, what(): "argument not found"
Of course, this is happening because all I'm doing is copying the replacement field after the ':' and before the '}', and respecting the {} balancing, so if I've used nested replacement fields, there will be a {} inside that refers to some argument from the original list, which is no-good for this.
My specialization for the user-defined type:
struct Vec2
{
float x;
float y;
};
template<>
struct fmt::formatter<Vec2>
{
auto parse(fmt::format_parse_context& ctx) -> decltype(ctx.begin())
{
int curlyBalance = 1;
auto it = ctx.begin(), end = ctx.end();
while (it != end)
{
if (*it == '}')
{
--curlyBalance;
}
else if (*it == '{')
{
++curlyBalance;
}
if (curlyBalance <= 0)
break;
else
++it;
}
const char* beginPtr = &(*ctx.begin());
const char* endPtr = &(*it);
size_t len = endPtr - beginPtr;
if (len == 0)
{
formatStr = "{}";
}
else
{
formatStr = "{0:";
formatStr += std::string(beginPtr, len + 1);
}
return it;
}
template <typename FormatContext>
auto format(const Vec2& vec, FormatContext& context)
{
fmt::format_to(context.out(), "(");
fmt::format_to(context.out(), formatStr, vec.x);
fmt::format_to(context.out(), ", ");
fmt::format_to(context.out(), formatStr, vec.y);
return fmt::format_to(context.out(), ")");
}
std::string formatStr;
};
int main()
{
std::cout << "Hello world!" << std::endl;
Vec2 v {1.234567, 2.345678};
// Simple, static width.
//std::string fmtResult = fmt::format("Hello '{0:<8.4f}' World!\n", v, 5);
// Dynamic width, oh god, oh dear god no!
std::string fmtResult = fmt::format("Hello '{0:<{1}}' World!\n", v, 5);
std::cout << fmtResult;
}
It seems that what needs to happen is my parse function needs to have access to the other args so it can fill in the nested replacement field with the correct value... but I'm still new to this library, and would greatly appreciate some help with this!
Godbolt link: https://godbolt.org/z/6fxWszTT8
You can reuse formatter<float> for this (https://godbolt.org/z/vb9c5ffd5):
template<> struct fmt::formatter<Vec2> : formatter<float> {
template <typename FormatContext>
auto format(const Vec2& vec, FormatContext& ctx) {
auto out = ctx.out();
*out = '(';
ctx.advance_to(out);
out = formatter<float>::format(vec.x, ctx);
out = fmt::format_to(out, ", ");
ctx.advance_to(out);
out = formatter<float>::format(vec.y, ctx);
*out = ')';
return out;
}
};

How to turn Variadic Templates into multiple single templates?(C++ Competitive Programming Debugging Template)

My debugging template is:
#define ts to_string
string ts(char c) { return string(1, c); }
string ts(bool b) { return b ? "true" : "false"; }
string ts(const char* s) { return (string)s; }
string ts(string s) { return s; }
template<class A> string ts(complex<A> c) {
stringstream ss; ss << c; return ss.str(); }
string ts(vector<bool> v) {
string res = "{"; for(int i = 0; i < si(v); ++i) res += char('0' + v[i]);
res += "}"; return res; }
template<size_t SZ> string ts(bitset<SZ> b) {
string res = ""; for(int i = 0; i < SZ; ++i) res += char('0' + b[i]);
return res; }
template<class A, class B> string ts(pair<A,B> p);
template<class T> string ts(T v) { // containers with begin(), end()
bool fst = 1; string res = "{";
for(const auto& x: v) {
if (!fst) res += ", ";
fst = 0; res += ts(x);
}
res += "}"; return res;
}
template<class A, class B> string ts(pair<A,B> p) {
return "(" + ts(p.f) + ", " + ts(p.s) + ")"; }
void DBG() { cerr << "]" << endl; }
template<class H, class... T> void DBG(H h, T... t) {
cerr << ts(h); if (sizeof...(t)) cerr << ", ";
DBG(t...); }
#ifdef LOCAL // compile with -DLOCAL
#define dbg(...) cerr << "[" << #__VA_ARGS__ << "]: [", DBG(__VA_ARGS__)
#else
#define dbg(...) 0
#endif
When I type
dbg(a, n);
where 'a' is the vector name and n is the size of the vector. 'a' contains the following {1, 2, 3, 4, 5} and n = 5
it prints
[a, n]: [{1, 2, 3, 4, 5}, 5]
but I want it to print
[a]: [{1, 2, 3, 4, 5}]
[n]: [5]
without having to type
dbg(a);
dbg(n);
Is there any way to do this?
When I type
dbg(a, n);
I want it to print
dbg(a);
dbg(n);
Is there any way to do this?
Overload a macro on number of arguments and invoke your callback in the overload for each argument.
// renamed from dbg
#define dbg_in(...) cerr << "[" << #__VA_ARGS__ << "]: [", DBG(__VA_ARGS__)
// overloads
#define dbg_1(_1) \
dbg_in(_1)
#define dbg_2(_1,_2) \
dbg_1(_1);dbg_in(_2)
#define dbg_3(_1,_2,_3) \
dbg_2(_1,_2);dbg_in(_3)
// etc.
#define dbg_N(_1,_2,_3,_4,_5,_6,_7,_8,_9,N,...) \
dbg_##N
#define dbg(...) \
dbg_N(__VA_ARGS__,9,8,7,6,5,4,3,2,1)(__VA_ARGS__)
dbg(a, b);
// expands to: dbg_in(a);dbg_in(b);
Codeforces community has helped me and told me the correct solution.
#define ts to_string
string ts(char c) { return string(1, c); }
string ts(bool b) { return b ? "true" : "false"; }
string ts(const char* s) { return (string)s; }
string ts(string s) { return s; }
template<class A> string ts(complex<A> c) {
stringstream ss; ss << c; return ss.str(); }
string ts(vector<bool> v) {
string res = "{"; for(int i = 0; i < si(v); ++i) res += char('0' + v[i]);
res += "}"; return res; }
template<size_t SZ> string ts(bitset<SZ> b) {
string res = ""; for(int i = 0; i < SZ; ++i) res += char('0' + b[i]);
return res; }
template<class A, class B> string ts(pair<A,B> p);
template<class T> string ts(T v) { // containers with begin(), end()
bool fst = 1; string res = "{";
for (const auto& x: v) {
if (!fst) res += ", ";
fst = 0; res += ts(x);
}
res += "}"; return res;
}
template<class A, class B> string ts(pair<A,B> p) {
return "(" + ts(p.f) + ", " + ts(p.s) + ")"; }
// DEBUG
void DBG(string names) { string s = names; }
template<class H, class... T> void DBG(string names, H h, T... t) {
auto pos = names.find(',');
auto first_name = names.substr(0, pos);
auto rest = names.substr(pos+1);
// Strip space at the beginning
while(rest.front() == ' '){
rest = rest.substr(1);
}
cerr << "[" << first_name << "]: [" << ts(h) << "]" << nl;
DBG(rest, t...);
}
#ifdef LOCAL
#define dbg(...) DBG(#__VA_ARGS__, __VA_ARGS__)
#else
#define dbg(...) 0
#endif
void EDBG() { cerr << "]" << endl; }
template<class H, class... T> void EDBG(H h, T... t) {
cerr << ts(h); if (sizeof...(t)) cerr << ", ";
EDBG(t...); }
#ifdef LOCAL // compile with -DLOCAL
#define edbg(...) cerr << "[" << #__VA_ARGS__ << "]: [", EDBG(__VA_ARGS__)
#else
#define edbg(...) 0
#endif
the macro
edbg
does not do it seperately so
edbg(a, n);
will output
edbg(a, n);
Whereas
dbg(a, n);
will output
dbg(a);
dbg(n);
The problem is that #__VA_ARGS__ doesn't return a list of strings, comma separated, with the names of the variables, but a single string, with the name of the variables comma separated.
So you have to split the string in some way.
If you can use C++17, I propose the following function that take a single string, with names comma separated, and return a std::vector<std::string> with single names
std::vector<std::string> splitWords (std::string const & s)
{
std::regex rgx ("\\w+");
return { std::sregex_token_iterator{s.begin(), s.end(), rgx},
std::sregex_token_iterator{} };
}
and also a variadic templates dbgh() (dbg helper) function as follows
template <typename ... Ts>
void dbgh (std::vector<std::string> v, Ts const & ... ts)
{
std::size_t i{};
((std::cerr << '[' << v[i++] << "]: [", DBG(ts)), ...);
}
so you can write the dbg() variadic macro as follows
#define dbg(...) dbgh(splitWords(#__VA_ARGS__), __VA_ARGS__)

C++11 for each loop with more than one variable

I would like to translate the following traditional for loop into a C++11 for-each loop without extra looping constructs:
int a[] = { 5, 6, 7, 8, 9, 10 };
int b[] = { 50, 60, 70, 80, 90, 100 };
// Swap a and b array elements
for (int i = 0; i < sizeof(a)/sizeof(a[0]); i++)
{
a[i] ^= b[i]; b[i] ^= a[i]; a[i] ^= b[i];
}
Does there exist any way by which it is possible to provide more than one variable in the C++11 for-each loop like:
for (int i, int j : ...)
There is no built-in way to do this. If you can use Boost, boost::combine will work for iterating two (or more) ranges simultaneously (Does boost offer make_zip_range?, How can I iterate over two vectors simultaneously using BOOST_FOREACH?):
for (boost::tuple<int&, int&> ij : boost::combine(a, b)) {
int& i = boost::get<0>(ij);
int& j = boost::get<1>(ij);
// ...
}
Unfortunately accessing the elements within the tuple elements of the zipped range is highly verbose. C++17 will make this much more readable using structured binding:
for (auto [&i, &j] : boost::combine(a, b)) {
// ...
}
Since you don't need to break out of the loop or return from the enclosing function, you could use boost::range::for_each with the body of your loop as a lambda:
boost::range::for_each(a, b, [](int& i, int& j)
{
// ...
});
zip or combine ranges are common in many range libraries.
Writing one strong enough for a for(:) loop isn't hard however.
First we write a basic range type:
template<class It>
struct range_t {
It b,e;
It begin() const{ return b; }
It end() const{ return e; }
range_t without_front( std::size_t count = 1 ) const {
return {std::next(begin()), end()};
}
bool empty() const { return begin()==end(); }
};
template<class It>
range_t<It> range( It b, It e ) { return {b,e}; }
template<class C>
auto range( C& c ) {
using std::begin; using std::end;
return range( begin(c), end(c) );
};
Then we write an iterator that works with ranges (easier than with iterators):
template<class R1, class R2>
struct double_foreach_iterator {
R1 r1;
R2 r2;
void operator++() { r1 = r1.without_front(); r2 = r2.without_front(); }
bool is_end() const { return r1.empty() || r2.empty(); }
auto operator*()const {
return std::tie( *r1.begin(), *r2.begin() );
}
using self=double_foreach_iterator;
auto cur() const {
return std::make_tuple( r1.begin(), r2.begin() );
}
friend bool operator==( self const& lhs, self const& rhs ) {
if (lhs.is_end() || rhs.is_end())
return lhs.is_end() == rhs.is_end();
return lhs.cur() == rhs.cur();
}
friend bool operator!=( self const& lhs, self const& rhs ) {
return !(lhs==rhs);
}
};
now we double iterate:
template<class A, class B>
auto zip_iterate(
A& a, B& b
) {
auto r1 = range(a);
auto r2 = range(b);
auto r1end = range(r1.end(), r1.end());
auto r2end = range(r2.end(), r2.end());
using it = double_foreach_iterator<decltype(r1), decltype(r2)>;
return range( it{r1, r2}, it{r1end, r2end} );
}
which gives us:
for (auto tup : zip_iterate(a, b)) {
int& i = std::get<0>(tup);
int& j = std::get<1>(tup);
// ...
}
or in C++17:
for (auto&& [i, j] : zip_iterate(a, b)) {
// ...
}
My zip iterate does not assume the two containers are of the same length, and will iterate to the length of the shorter one.
live example.
Just for fun.
The following isn't intended to be a serious answer to the question but just an exercise to try to understand the potentiality of C++11 (so, please, be patient).
The following is an example of a class (a draft of a class) that receive a couple of container (with size() method), with the same size (exception otherwise), and of a custom iterator that return a std::pair of std::reference_wrapper to n-position elements.
With a simple use example that show that it's possible to change the value in the starting containers.
Doesn't work with old C-style arrays but works with std::array. We're talking about C++11 so I suppose we could impose the use of std::array.
#include <array>
#include <vector>
#include <iostream>
#include <functional>
template <typename T1, typename T2>
class pairWrapper
{
public:
using V1 = typename std::remove_reference<decltype((T1().at(0)))>::type;
using V2 = typename std::remove_reference<decltype((T2().at(0)))>::type;
using RW1 = std::reference_wrapper<V1>;
using RW2 = std::reference_wrapper<V2>;
class it
{
public:
it (pairWrapper & pw0, std::size_t p0): pos{p0}, pw{pw0}
{ }
it & operator++ ()
{ ++pos; return *this; }
bool operator!= (const it & it0)
{ return pos != it0.pos; }
std::pair<RW1, RW2> & operator* ()
{
static std::pair<RW1, RW2>
p{std::ref(pw.t1[0]), std::ref(pw.t2[0])};
p.first = std::ref(pw.t1[pos]);
p.second = std::ref(pw.t2[pos]);
return p;
}
private:
std::size_t pos;
pairWrapper & pw;
};
it begin()
{ return it(*this, 0U); }
it end()
{ return it(*this, len); }
pairWrapper (T1 & t10, T2 & t20) : len{t10.size()}, t1{t10}, t2{t20}
{ if ( t20.size() != len ) throw std::logic_error("no same len"); }
private:
const std::size_t len;
T1 & t1;
T2 & t2;
};
template <typename T1, typename T2>
pairWrapper<T1, T2> makePairWrapper (T1 & t1, T2 & t2)
{ return pairWrapper<T1, T2>(t1, t2); }
int main()
{
std::vector<int> v1 { 1, 2, 3, 4 };
std::array<long, 4> v2 { { 11L, 22L, 33L, 44L } };
for ( auto & p : makePairWrapper(v1, v2) )
{
std::cout << '{' << p.first << ", " << p.second << '}' << std::endl;
p.first += 3;
p.second += 55;
}
for ( const auto & i : v1 )
std::cout << '[' << i << ']' << std::endl;
for ( const auto & l : v2 )
std::cout << '[' << l << ']' << std::endl;
return 0;
}
p.s.: sorry for my bad English

Boost.Spirit parse string to number with radix

I have a template function which casts string to number as following:
template <typename RetType,
typename Parser =
typename boost::spirit::traits::create_parser<RetType>::type>
inline std::enable_if_t<std::is_arithmetic<RetType>::value, RetType>
cast(const std::string &input)
{
RetType result;
if(input.empty())
{
// handle this
}
auto itBeg = input.cbegin();
auto itEnd = input.cend();
if(!bsq::parse(itBeg, itEnd, Parser(), result) || itBeg != itEnd)
{
// handle that
}
return result;
}
now I would like to create a function similar to above which will parse string that represents a number in some radix
template <typename RetType, unsigned Radix,
typename Parser =
typename boost::spirit::traits::create_parser<RetType>::type>
inline std::enable_if_t<std::is_arithmetic<RetType>::value, RetType>
cast(const std::string &input)
{
RetType result;
if(input.empty())
{
// handle this
}
auto itBeg = input.cbegin();
auto itEnd = input.cend();
if(!bsq::parse(itBeg, itEnd, Parser<RetType, Radix, 1 - 1>() /*something like this*/, result) || itBeg != itEnd)
{
// handle that
}
return result;
}
the Parser is invalid, of course, but what is the right way to define "automatic" arithmetic parser with radix?
I'd use qi::int_parser<> directly:
Live On Coliru
#include <boost/spirit/include/qi.hpp>
#include <type_traits>
template <typename RetType, unsigned Radix = 10, typename Parser = typename boost::spirit::qi::int_parser<RetType, Radix> >
inline typename std::enable_if<std::is_arithmetic<RetType>::value, RetType>::type
cast(const std::string &input)
{
RetType result;
if(input.empty())
{
// handle this
}
auto itBeg = input.cbegin();
auto itEnd = input.cend();
if(!boost::spirit::qi::parse(itBeg, itEnd, Parser(), result) || itBeg != itEnd)
{
// handle that
throw "oops";
}
return result;
}
int main() {
std::cout << cast<int> ("10") << "\n";
std::cout << cast<int, 2>("10") << "\n";
std::cout << cast<int, 8>("10") << "\n";
std::cout << cast<int, 16>("10") << "\n";
std::cout << cast<int, 16>("ee") << "\n";
}
Prints
10
2
8
16
238
Hint: to be very accurate you might want to detect signed/unsigned types and use uint_parser<> accordingly

Elegantly (iterating) parsing data in chunks?

We have some "iterable" collection of data, for instance: std::vector<Foo> bar.
We wish to process Foo elements from bar until some condition is met in which point we "yield" (think Python) the result of all these processed Foos and wait until the next chunk of parsed information is requested.
So far what we're doing is this:
ParsedChunk foobar( std::vector<Foo> bar, size_t* start_from) {
size_t& i = *start_from;
ParsedChunk result_so_far;
for (;i < bar.size(); i++) {
process_some_foo_and_update_chunk(result_so_far, bar[i]);
if (check_condition(? ? ?) {
return result_so_far;
}
}
}
Any suggestions for doing this better?
As I already pointed out in my comment, this is IMO a very good case for an custom iterator:
The iterator scans through your range, as long as some predicate holds, and
when the predicate isn't true for some element, calls a function with the sub range of elements where the predicate held (plus the one that didn't satisfy the predicate). The result of that function call is then the value you get when you dereference the iterator.
template<typename Fn, typename Predicate, typename Iterator>
struct collector {
using value_type = typename std::result_of<Fn(Iterator, Iterator)>::type;
using pointer = value_type const *;
using reference = value_type const &;
using difference_type = std::ptrdiff_t;
using iterator_category = std::forward_iterator_tag;
value_type cache;
Fn fn;
Predicate predicate;
Iterator pos, from, stop;
collector(Fn&& fn, Predicate&& p, Iterator&& s, Iterator&& e)
: fn(std::forward<Fn>(fn)),
predicate(std::forward<Predicate>(p)),
pos(std::forward<Iterator>(s)),
from(pos),
stop(std::forward<Iterator>(e))
{
next_range();
}
collector & operator++(void) {
next_range();
return *this;
}
reference operator*(void) const {
return cache;
}
void next_range(void) {
from = pos;
if (pos == stop) return;
for (; pos != stop; ++pos) {
if (not predicate(*pos)) {
++pos;
break;
}
}
cache = fn(from, pos);
}
collector end_of_range(void) const {
auto copy = collector{*this};
copy.pos = copy.stop;
copy.from = copy.stop;
return copy;
}
bool operator==(collector const & rhs) const {
return (from == rhs.from) and (pos == rhs.pos) and (stop == rhs.stop);
}
bool operator!=(collector const & rhs) const {
return (from != rhs.from) or (pos != rhs.pos) or (stop != rhs.stop);
}
};
template<typename Fn, typename Predicate, typename Iterator>
auto make_collector_range(Fn&& fn, Predicate&& p, Iterator&& s, Iterator&& e) {
using I = typename std::decay<Iterator>::type;
using P = typename std::decay<Predicate>::type;
using F = typename std::decay<Fn>::type;
using C = collector<F,P,I>;
auto start = C{
std::forward<Fn>(fn), std::forward<Predicate>(p),
std::forward<Iterator>(s), std::forward<Iterator>(e)};
auto stop = start.end_of_range();
return make_pair(std::move(start), std::move(stop));
}
An example usage, calculating the sum of the numbers till 50, but not in one step, but in steps of 15 numbers each:
int main(int, char**) {
vector<int> numbers = vector<int>(50);
generate(begin(numbers), end(numbers),
[i = 0] (void) mutable{
return ++i;
});
copy(begin(numbers), end(numbers), ostream_iterator<int>{cout, " "});
cout << endl;
auto collected = make_collector_range(
[](auto const & from, auto const & to) {
return accumulate(from, to, 0);
},
[](auto const & num) {
return not ((num % 3 == 0) and (num % 5 == 0));
},
begin(numbers), end(numbers));
copy(collected.first, collected.second, ostream_iterator<int>{cout, " "});
cout << endl;
bool passed = accumulate(collected.first, collected.second, 0) == (50*51)/2;
cout << "test " << (passed ? "passed" : "failed") << endl;
return 0;
}
(Live demo here)
(Note: This example uses a fixed "step" width, and predicate and function are unrelated to each other and don't maintain state, but none of this is required by the iterator.)
I hope the intention of the code is clear, if not I can try to provide a more detailed explanation about its workings.