A library for working with phylogenetic and population genetic data.
v0.27.0
tree/formats/newick/input_iterator.hpp
Go to the documentation of this file.
1 #ifndef GENESIS_TREE_FORMATS_NEWICK_INPUT_ITERATOR_H_
2 #define GENESIS_TREE_FORMATS_NEWICK_INPUT_ITERATOR_H_
3 
4 /*
5  Genesis - A toolkit for working with phylogenetic data.
6  Copyright (C) 2014-2020 Lucas Czech and HITS gGmbH
7 
8  This program is free software: you can redistribute it and/or modify
9  it under the terms of the GNU General Public License as published by
10  the Free Software Foundation, either version 3 of the License, or
11  (at your option) any later version.
12 
13  This program is distributed in the hope that it will be useful,
14  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  GNU General Public License for more details.
17 
18  You should have received a copy of the GNU General Public License
19  along with this program. If not, see <http://www.gnu.org/licenses/>.
20 
21  Contact:
22  Lucas Czech <lucas.czech@h-its.org>
23  Exelixis Lab, Heidelberg Institute for Theoretical Studies
24  Schloss-Wolfsbrunnenweg 35, D-69118 Heidelberg, Germany
25 */
26 
34 #include "genesis/tree/tree.hpp"
38 
39 #include <iterator>
40 
41 namespace genesis {
42 namespace tree {
43 
44 // =================================================================================================
45 // Newick Input Iterator
46 // =================================================================================================
47 
77 {
78 public:
79 
80  // -------------------------------------------------------------------------
81  // Member Types
82  // -------------------------------------------------------------------------
83 
85  using iterator_category = std::input_iterator_tag;
86 
87  // -------------------------------------------------------------------------
88  // Constructors and Rule of Five
89  // -------------------------------------------------------------------------
90 
95  : input_stream_( nullptr )
96  , reader_()
97  , tree_()
98  {}
99 
103  explicit NewickInputIterator( std::shared_ptr<utils::BaseInputSource> source )
104  : input_stream_( std::make_shared<utils::InputStream>( source ))
105  , reader_()
106  , tree_()
107  {
108  // Setting so that we only read one tree at a time.
109  reader_.stop_after_semicolon( true );
110 
111  // Read first tree.
112  increment();
113  }
114 
119  NewickInputIterator( std::shared_ptr<utils::BaseInputSource> source, NewickReader const& settings )
120  : input_stream_( std::make_shared<utils::InputStream>( source ))
121  , reader_( settings )
122  , tree_()
123  {
124  // Setting so that we only read one tree at a time.
125  reader_.stop_after_semicolon( true );
126 
127  // Read first tree.
128  increment();
129  }
130 
131  ~NewickInputIterator() = default;
132 
133  NewickInputIterator( self_type const& ) = delete;
134  NewickInputIterator( self_type&& ) = default;
135 
136  self_type& operator= ( self_type const& ) = delete;
137  self_type& operator= ( self_type&& ) = default;
138 
139  // -------------------------------------------------------------------------
140  // Comparators
141  // -------------------------------------------------------------------------
142 
143  bool operator == ( self_type const& other ) const
144  {
145  return input_stream_ == other.input_stream_;
146  }
147 
148  bool operator != ( self_type const& other ) const
149  {
150  return !( *this == other );
151  }
152 
156  explicit operator bool() const
157  {
158  return good_;
159  }
160 
161  // -------------------------------------------------------------------------
162  // Accessors
163  // -------------------------------------------------------------------------
164 
165  Tree const& operator * () const
166  {
167  return dereference();
168  }
169 
170  Tree const* operator -> () const
171  {
172  return &dereference();
173  }
174 
175  Tree const& dereference() const
176  {
177  return tree_;
178  }
179 
180  // -------------------------------------------------------------------------
181  // Iteration
182  // -------------------------------------------------------------------------
183 
191  {
192  return *this;
193  }
194 
201  {
202  return self_type();
203  }
204 
206  {
207  increment();
208  return *this;
209  }
210 
211  void increment()
212  {
213  // Check whether the input stream is good (not end-of-stream) and can be read from.
214  // If not, we reached its end, so we stop reading in the next iteration.
215  if( ! input_stream_ || ! *input_stream_ ) {
216  good_ = false;
217  return;
218  }
219 
220  // Read the next tree.
221  tree_ = reader_.parse_single_tree( *input_stream_ );
222 
223  // Check whether we actually got a tree. We use empty as marker for this,
224  // which is valid, as we can never read an actual empty tree from any input
225  // (it always consists of at least the root node).
226  if( tree_.empty() ) {
227  good_ = false;
228  }
229  }
230 
231  // -------------------------------------------------------------------------
232  // Data Members
233  // -------------------------------------------------------------------------
234 
235 private:
236 
237  std::shared_ptr<utils::InputStream> input_stream_;
238 
239  bool good_ = true;
240  NewickReader reader_;
241  Tree tree_;
242 };
243 
244 } // namespace tree
245 } // namespace genesis
246 
247 #endif // include guard
genesis::tree::NewickReader::stop_after_semicolon
NewickReader & stop_after_semicolon(bool value)
Set whether reading a single tree stops after the semicolon that finishes a Newick tree.
Definition: tree/formats/newick/reader.cpp:844
genesis::tree::NewickInputIterator::self_type
NewickInputIterator self_type
Definition: tree/formats/newick/input_iterator.hpp:84
genesis::tree::NewickInputIterator::operator!=
bool operator!=(self_type const &other) const
Definition: tree/formats/newick/input_iterator.hpp:148
genesis::tree::NewickReader
Definition: tree/formats/newick/reader.hpp:67
genesis::tree::NewickInputIterator::iterator_category
std::input_iterator_tag iterator_category
Definition: tree/formats/newick/input_iterator.hpp:85
genesis::tree::NewickInputIterator::operator==
bool operator==(self_type const &other) const
Definition: tree/formats/newick/input_iterator.hpp:143
genesis::tree::NewickInputIterator::operator*
Tree const & operator*() const
Definition: tree/formats/newick/input_iterator.hpp:165
genesis::tree::NewickInputIterator::operator++
self_type & operator++()
Definition: tree/formats/newick/input_iterator.hpp:205
tree.hpp
Header of Tree class.
genesis::tree::NewickInputIterator::~NewickInputIterator
~NewickInputIterator()=default
genesis::tree::NewickInputIterator::NewickInputIterator
NewickInputIterator()
Create a default instance, with no input.
Definition: tree/formats/newick/input_iterator.hpp:94
genesis::tree::NewickInputIterator
Iterate an input stream and parse it as Newick trees.
Definition: tree/formats/newick/input_iterator.hpp:76
input_source.hpp
input_stream.hpp
genesis::tree::NewickInputIterator::dereference
Tree const & dereference() const
Definition: tree/formats/newick/input_iterator.hpp:175
genesis::tree::Tree
Class for representing phylogenetic trees.
Definition: tree/tree.hpp:97
genesis::tree::Tree::empty
bool empty() const
Return whether the Tree is empty (i.e., has no nodes, edges and links).
Definition: tree/tree.hpp:194
genesis::tree::NewickInputIterator::end
self_type end()
End of the iterator.
Definition: tree/formats/newick/input_iterator.hpp:200
genesis
Container namespace for all symbols of genesis in order to keep them separate when used as a library.
Definition: placement/formats/edge_color.cpp:42
genesis::tree::NewickInputIterator::NewickInputIterator
NewickInputIterator(std::shared_ptr< utils::BaseInputSource > source)
Create an instance that reads from an input source, using a default NewickReader.
Definition: tree/formats/newick/input_iterator.hpp:103
reader.hpp
genesis::tree::NewickInputIterator::NewickInputIterator
NewickInputIterator(std::shared_ptr< utils::BaseInputSource > source, NewickReader const &settings)
Create an instance that reads from an input source, using the settings of a given NewickReader.
Definition: tree/formats/newick/input_iterator.hpp:119
genesis::tree::NewickInputIterator::begin
self_type & begin()
Beginning of the iterator.
Definition: tree/formats/newick/input_iterator.hpp:190
genesis::tree::NewickInputIterator::increment
void increment()
Definition: tree/formats/newick/input_iterator.hpp:211
genesis::tree::NewickInputIterator::operator->
Tree const * operator->() const
Definition: tree/formats/newick/input_iterator.hpp:170
genesis::tree::NewickInputIterator::operator=
self_type & operator=(self_type const &)=delete
genesis::tree::NewickReader::parse_single_tree
Tree parse_single_tree(utils::InputStream &input_stream) const
Parse a single tree. Depending on stop_after_semicolon(), stop after the semicolon or continue until ...
Definition: tree/formats/newick/reader.cpp:102