| 1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465 |
- //
- // filter_iterator.hpp
- // iterator
- //
- // Created by Sam Jaffe on 6/17/17.
- //
- #pragma once
- #include "end_aware_iterator.hpp"
- namespace iterator {
- template <typename Iter>
- class filter_iterator : public end_aware_iterator<Iter> {
- private:
- using super = end_aware_iterator<Iter>;
- public:
- using value_type = typename super::value_type;
- using reference = typename super::reference;
- using pointer = typename super::pointer;
- using difference_type = typename super::difference_type;
- using iterator_category = typename super::iterator_category;
- public:
- filter_iterator() = default;
- template <typename... Args>
- filter_iterator(std::function<bool(value_type const &)> && p, Args &&... super_args)
- : super(std::forward<Args>(super_args)...)
- , pred(std::move(p)) {
- if (should_advance()) { advance(); }
- }
-
- filter_iterator & operator++() {
- advance();
- return *this;
- }
-
- filter_iterator operator++(int) {
- filter_iterator tmp{*this};
- operator++();
- return tmp;
- }
- private:
- bool should_advance() {
- return !super::done() && !pred(super::operator*());
- }
- void advance() {
- do { super::operator++(); } while (should_advance());
- }
- std::function<bool(value_type const &)> pred;
- };
- }
- template <typename Pred, typename Iter>
- iterator::filter_iterator<Iter> make_filter_iterator(Pred && p, Iter it, Iter end) { return {p, it, end}; }
- template <typename Pred, typename C>
- auto make_filter_iterator(Pred && p, C & collect) -> iterator::filter_iterator<decltype(std::begin(collect))> {
- return { p, std::begin(collect), std::end(collect) };
- }
- template <typename Pred, typename C>
- auto make_filter_iterator(Pred && p, C const & collect) -> iterator::filter_iterator<decltype(std::begin(collect))> {
- return { p, std::begin(collect), std::end(collect) };
- }
|