소스 검색

fix: iota had some problems

Sam Jaffe 2 년 전
부모
커밋
7c992697cd
3개의 변경된 파일35개의 추가작업 그리고 19개의 파일을 삭제
  1. 1 1
      external/iterator
  2. 22 18
      include/stream/iota_view.h
  3. 12 0
      test/stream_test.cxx

+ 1 - 1
external/iterator

@@ -1 +1 @@
-Subproject commit ef9f846c790f6538dbf6bec1b00a90a95da89206
+Subproject commit 42718949c26af985aa593d0284a0498607f5d5d1

+ 22 - 18
include/stream/iota_view.h

@@ -10,27 +10,29 @@
 #include <iterator/facade.h>
 
 namespace stream::ranges {
-template <typename T, typename Bound> struct iota_view {
+template <typename T, typename Bound>
+class iota_iterator : public facade<iota_iterator<T, Bound>> {
 public:
-  constexpr static inline bool has_size_v = std::is_constructible_v<T, Bound>;
+  using sentinal_type = Bound;
 
-  class iterator : facade<iterator> {
-  public:
-    using sentinal_type = Bound;
+  iota_iterator() = default;
+  iota_iterator(T value, Bound bound) : value_(value), bound_(bound) {}
 
-    iterator(T value, Bound bound) : value_(value), bound_(bound) {}
+  T const & dereference() const { return value_; }
+  void increment() { ++value_; }
+  bool at_end() const { return value_ == bound_; }
+  std::ptrdiff_t distance_to(iota_iterator const & other) const {
+    return other.value_ - value_;
+  }
 
-    T const & dereference() const { return value_; }
-    void increment() const { ++value_; }
-    bool at_end() const { return value_ == bound_; }
-    std::ptrdiff_t distance_to(iterator const & other) const {
-      return other.value_ - value_;
-    }
+private:
+  T value_;
+  Bound bound_;
+};
 
-  private:
-    T value_;
-    Bound bound_;
-  };
+template <typename T, typename Bound> struct iota_view {
+public:
+  constexpr static inline bool has_size_v = std::is_constructible_v<T, Bound>;
 
 private:
   T value_;
@@ -39,10 +41,10 @@ private:
 public:
   iota_view(T value, Bound bound) : value_(value), bound_(bound) {}
 
-  auto begin() const { return iterator(value_, bound_); }
+  auto begin() const { return iota_iterator(value_, bound_); }
   auto end() const {
     if constexpr (has_size_v) {
-      return iterator(bound_, bound_);
+      return iota_iterator(bound_, bound_);
     } else {
       return bound_;
     }
@@ -60,3 +62,5 @@ template <typename T, typename Bound> auto iota(T value, Bound bound) {
   return iota_view(value, bound);
 }
 }
+
+MAKE_ITERATOR_FACADE_TYPEDEFS_T(stream::ranges::iota_iterator);

+ 12 - 0
test/stream_test.cxx

@@ -211,3 +211,15 @@ TEST(StreamTest, CanMapToMemFn) {
 //
 //  EXPECT_THAT(first, second);
 //}
+
+TEST(StreamTest, Iota) {
+  static_assert(iterator::detail::has_distance_to_v<
+                    stream::ranges::iota_iterator<int, int>>,
+                "");
+  auto out = views::iota(0, 4) |
+             views::transform([](size_t i) { return std::vector(i, i); }) |
+             views::join() | ranges::to_vector();
+
+  std::vector<size_t> expected{1, 2, 2, 3, 3, 3};
+  EXPECT_THAT(out, expected);
+}