1/* A forward filtered iterator for GDB, the GNU debugger. 2 Copyright (C) 2018-2023 Free Software Foundation, Inc. 3 4 This file is part of GDB. 5 6 This program is free software; you can redistribute it and/or modify 7 it under the terms of the GNU General Public License as published by 8 the Free Software Foundation; either version 3 of the License, or 9 (at your option) any later version. 10 11 This program is distributed in the hope that it will be useful, 12 but WITHOUT ANY WARRANTY; without even the implied warranty of 13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 GNU General Public License for more details. 15 16 You should have received a copy of the GNU General Public License 17 along with this program. If not, see <http://www.gnu.org/licenses/>. */ 18 19#ifndef COMMON_FILTERED_ITERATOR_H 20#define COMMON_FILTERED_ITERATOR_H 21 22/* A filtered iterator. This wraps BaseIterator and automatically 23 skips elements that FilterFunc filters out. Requires that 24 default-constructing a BaseIterator creates a valid one-past-end 25 iterator. */ 26 27template<typename BaseIterator, typename FilterFunc> 28class filtered_iterator 29{ 30public: 31 typedef filtered_iterator self_type; 32 typedef typename BaseIterator::value_type value_type; 33 typedef typename BaseIterator::reference reference; 34 typedef typename BaseIterator::pointer pointer; 35 typedef typename BaseIterator::iterator_category iterator_category; 36 typedef typename BaseIterator::difference_type difference_type; 37 38 /* Construct by forwarding all arguments to the underlying 39 iterator. */ 40 template<typename... Args> 41 explicit filtered_iterator (Args &&...args) 42 : m_it (std::forward<Args> (args)...) 43 { skip_filtered (); } 44 45 /* Create a one-past-end iterator. */ 46 filtered_iterator () = default; 47 48 /* Need these as the variadic constructor would be a better match 49 otherwise. */ 50 filtered_iterator (filtered_iterator &) = default; 51 filtered_iterator (const filtered_iterator &) = default; 52 filtered_iterator (filtered_iterator &&) = default; 53 filtered_iterator (const filtered_iterator &&other) 54 : filtered_iterator (static_cast<const filtered_iterator &> (other)) 55 {} 56 57 value_type operator* () const { return *m_it; } 58 59 self_type &operator++ () 60 { 61 ++m_it; 62 skip_filtered (); 63 return *this; 64 } 65 66 bool operator== (const self_type &other) const 67 { return m_it == other.m_it; } 68 69 bool operator!= (const self_type &other) const 70 { return m_it != other.m_it; } 71 72private: 73 74 void skip_filtered () 75 { 76 for (; m_it != m_end; ++m_it) 77 if (m_filter (*m_it)) 78 break; 79 } 80 81private: 82 FilterFunc m_filter {}; 83 BaseIterator m_it {}; 84 BaseIterator m_end {}; 85}; 86 87#endif /* COMMON_FILTERED_ITERATOR_H */ 88