SeqAn3
persist.hpp
Go to the documentation of this file.
1 // ============================================================================
2 // SeqAn - The Library for Sequence Analysis
3 // ============================================================================
4 //
5 // Copyright (c) 2006-2018, Knut Reinert & Freie Universitaet Berlin
6 // Copyright (c) 2016-2018, Knut Reinert & MPI Molekulare Genetik
7 // All rights reserved.
8 //
9 // Redistribution and use in source and binary forms, with or without
10 // modification, are permitted provided that the following conditions are met:
11 //
12 // * Redistributions of source code must retain the above copyright
13 // notice, this list of conditions and the following disclaimer.
14 // * Redistributions in binary form must reproduce the above copyright
15 // notice, this list of conditions and the following disclaimer in the
16 // documentation and/or other materials provided with the distribution.
17 // * Neither the name of Knut Reinert or the FU Berlin nor the names of
18 // its contributors may be used to endorse or promote products derived
19 // from this software without specific prior written permission.
20 //
21 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 // ARE DISCLAIMED. IN NO EVENT SHALL KNUT REINERT OR THE FU BERLIN BE LIABLE
25 // FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26 // DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
27 // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
28 // CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29 // LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30 // OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
31 // DAMAGE.
32 //
33 // ============================================================================
34 
40 #pragma once
41 
42 #include <range/v3/algorithm/copy.hpp>
43 
47 #include <seqan3/io/exception.hpp>
48 #include <seqan3/range/concept.hpp>
52 #include <seqan3/std/concepts>
53 #include <seqan3/std/ranges>
55 
56 namespace seqan3::detail
57 {
58 
59 // ============================================================================
60 // view_persist
61 // ============================================================================
62 
74 template <std::ranges::InputRange urng_t>
75 class view_persist : public ranges::view_interface<view_persist<urng_t>>
76 {
77 private:
79  std::shared_ptr<urng_t> urange;
80 
81 public:
85  using reference = reference_t<urng_t>;
88  using const_reference = std::conditional_t<const_iterable_concept<urng_t>, reference, void>;
90  using value_type = value_type_t<urng_t>;
92  using size_type = detail::transformation_trait_or_t<seqan3::size_type<urng_t>, void>;
94  using difference_type = difference_type_t<urng_t>;
96  using iterator = std::ranges::iterator_t<urng_t>;
98  using const_iterator = std::conditional_t<const_iterable_concept<urng_t>, iterator, void>;
100 
104  view_persist() = default;
105  constexpr view_persist(view_persist const & rhs) = default;
106  constexpr view_persist(view_persist && rhs) = default;
107  constexpr view_persist & operator=(view_persist const & rhs) = default;
108  constexpr view_persist & operator=(view_persist && rhs) = default;
109  ~view_persist() = default;
110 
114  view_persist(urng_t && _urange) :
115  urange{new urng_t{std::move(_urange)}}
116  {}
118 
135  iterator begin() noexcept
136  {
137  return seqan3::begin(*urange);
138  }
139 
141  const_iterator begin() const noexcept
142  requires const_iterable_concept<urng_t>
143  {
144  return seqan3::begin(*urange);
145  }
146 
148  const_iterator cbegin() const noexcept
149  requires const_iterable_concept<urng_t>
150  {
151  return seqan3::begin(*urange);
152  }
153 
167  auto end() noexcept
168  {
169  return seqan3::end(*urange);
170  }
171 
173  auto end() const noexcept
174  requires const_iterable_concept<urng_t>
175  {
176  return seqan3::end(*urange);
177  }
178 
180  auto cend() const noexcept
181  requires const_iterable_concept<urng_t>
182  {
183  return seqan3::end(*urange);
184  }
186 
192  template <sequence_container_concept container_t>
193  operator container_t()
195  requires std::CommonReference<reference_t<container_t>, reference>
197  {
198  container_t ret;
200  return ret;
201  }
202 
204  template <sequence_container_concept container_t>
205  operator container_t() const
207  requires std::CommonReference<reference_t<container_t>, reference> && const_iterable_concept<urng_t>
209  {
210  container_t ret;
212  return ret;
213  }
214 };
215 
218 template <typename urng_t>
219 view_persist(urng_t const &) -> view_persist<std::remove_reference_t<urng_t>>;
220 
221 // ============================================================================
222 // persist_fn (adaptor definition)
223 // ============================================================================
224 
227 class persist_fn : public pipable_adaptor_base<persist_fn>
228 {
229 private:
231  using base_t = pipable_adaptor_base<persist_fn>;
232 
233 public:
235  using base_t::base_t;
236 
237 private:
239  friend base_t;
240 
244  template <std::ranges::ViewableRange urng_t>
245  static auto impl(urng_t && urange)
246  {
247  return view::all(std::forward<urng_t>(urange));
248  }
249 
253  template <std::ranges::Range urng_t>
254  static auto impl(urng_t && urange)
255  {
256  static_assert(!std::is_lvalue_reference_v<urng_t>, "BUG: lvalue-reference in persist_fn::impl().");
257  return view_persist{std::move(urange)};
258  }
259 };
260 
261 } // namespace seqan3::detail
262 
263 // ============================================================================
264 // view::persist (adaptor instance definition)
265 // ============================================================================
266 
267 namespace seqan3::view
268 {
269 
315 inline auto constexpr persist = detail::persist_fn{};
316 
318 
319 } // namespace seqan3::view
::ranges::cbegin cbegin
Alias for ranges::cbegin. Returns an iterator to the beginning of a range.
Definition: ranges:245
Provides exceptions used in the I/O module.
Contains various shortcuts for common std::ranges functions.
Provides seqan3::detail::transformation_trait_or.
SeqAn specific customisations in the standard namespace.
Definition: align_result.hpp:221
::ranges::copy copy
Alias for ranges::copy. Copies a range of elements to a new location.
Definition: ranges:200
t & operator=(t1 const &rhs)
Assignment operator.
Additional non-standard concepts for ranges.
The Concepts library.
Auxiliary header for the view submodule .
::ranges::iterator_t iterator_t
Alias for ranges::iterator_t. Obtains the iterator type of a range.
Definition: ranges:225
Adaptations of concepts from the Ranges TS.
::ranges::begin begin
Alias for ranges::begin. Returns an iterator to the beginning of a range.
Definition: ranges:185
Provides seqan3::view::all.
The SeqAn3 namespace for views.
auto constexpr persist
A view adaptor that wraps rvalue references of non-views.
Definition: persist.hpp:315
Definition: aligned_sequence_concept.hpp:288
typename reference< t >::type reference_t
Type metafunction shortcut for seqan3::reference.
Definition: pre.hpp:98
constexpr auto all
A view that safely wraps a container (you will likely not need to use this unless defining a new view...
Definition: view_all.hpp:95
Provides various metafunctions used by the range module.
Provides various metafunctions for use on iterators.
::ranges::cend cend
Alias for ranges::cend. Returns an iterator to the end of a range.
Definition: ranges:250
Adaptations of concepts from the standard library.
constexpr auto back_inserter(container_t &container)
Create a std::back_insert_iterator for the argument.
Definition: iterator:79
::ranges::end end
Alias for ranges::end. Returns an iterator to the end of a range.
Definition: ranges:190