[llvm] r282804 - Add llvm::enumerate() to STLExtras.

Zachary Turner via llvm-commits llvm-commits at lists.llvm.org
Thu Sep 29 16:22:37 PDT 2016


Already reverted, sorry for the trouble.

On Thu, Sep 29, 2016 at 4:13 PM Rafael EspĂ­ndola <rafael.espindola at gmail.com>
wrote:

> Looks like this broke the build with clang:
>
> /home/espindola/llvm/llvm-project/llvm/include/llvm/ADT/STLExtras.h:632:22:
> error: declaration of 'V' shadows template parameter
>   template <typename V> struct result_pair {
>
> Cheers,
> Rafael
>
>
> On 29 September 2016 at 15:59, Zachary Turner via llvm-commits
> <llvm-commits at lists.llvm.org> wrote:
> > Author: zturner
> > Date: Thu Sep 29 17:59:30 2016
> > New Revision: 282804
> >
> > URL: http://llvm.org/viewvc/llvm-project?rev=282804&view=rev
> > Log:
> > Add llvm::enumerate() to STLExtras.
> >
> > enumerate allows you to iterate over a range by pairing the
> > iterator's value with its index in the enumeration.  This gives
> > you most of the benefits of using a for loop while still allowing
> > the range syntax.
> >
> > Modified:
> >     llvm/trunk/include/llvm/ADT/STLExtras.h
> >     llvm/trunk/unittests/ADT/STLExtrasTest.cpp
> >
> > Modified: llvm/trunk/include/llvm/ADT/STLExtras.h
> > URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ADT/STLExtras.h?rev=282804&r1=282803&r2=282804&view=diff
> >
> ==============================================================================
> > --- llvm/trunk/include/llvm/ADT/STLExtras.h (original)
> > +++ llvm/trunk/include/llvm/ADT/STLExtras.h Thu Sep 29 17:59:30 2016
> > @@ -626,6 +626,73 @@ template <typename T> struct deref {
> >    }
> >  };
> >
> > +namespace detail {
> > +template <typename I, typename V> class enumerator_impl {
> > +public:
> > +  template <typename V> struct result_pair {
> > +    result_pair(std::size_t Index, V Value) : Index(Index),
> Value(Value) {}
> > +
> > +    const std::size_t Index;
> > +    V Value;
> > +  };
> > +
> > +  template <typename I, typename V> struct iterator {
> > +    iterator(I Iter, std::size_t Index) : Iter(Iter), Index(Index) {}
> > +
> > +    result_pair<const V> operator*() const {
> > +      return result_pair<const V>(Index, *Iter);
> > +    }
> > +    result_pair<V> operator*() { return result_pair<V>(Index, *Iter); }
> > +
> > +    iterator &operator++() {
> > +      ++Iter;
> > +      ++Index;
> > +      return *this;
> > +    }
> > +
> > +    bool operator!=(const iterator &RHS) const { return Iter !=
> RHS.Iter; }
> > +
> > +  private:
> > +    I Iter;
> > +    std::size_t Index;
> > +  };
> > +
> > +  enumerator_impl(I Begin, I End)
> > +      : Begin(std::move(Begin)), End(std::move(End)) {}
> > +
> > +  iterator<I, V> begin() { return iterator<I, V>(Begin, 0); }
> > +  iterator<I, V> end() { return iterator<I, V>(End, std::size_t(-1)); }
> > +
> > +  iterator<I, V> begin() const { return iterator<I, V>(Begin, 0); }
> > +  iterator<I, V> end() const { return iterator<I, V>(End,
> std::size_t(-1)); }
> > +
> > +private:
> > +  I Begin;
> > +  I End;
> > +};
> > +}
> > +
> > +/// Given an input range, returns a new range whose values are are pair
> (A,B)
> > +/// such that A is the 0-based index of the item in the sequence, and B
> is
> > +/// the value from the original sequence.  Example:
> > +///
> > +/// std::vector<char> Items = {'A', 'B', 'C', 'D'};
> > +/// for (auto X : enumerate(Items)) {
> > +///   printf("Item %d - %c\n", X.Item, X.Value);
> > +/// }
> > +///
> > +/// Output:
> > +///   Item 0 - A
> > +///   Item 1 - B
> > +///   Item 2 - C
> > +///   Item 3 - D
> > +///
> > +template <typename R> auto enumerate(R &&Range) {
> > +  typedef decltype(std::begin(Range)) I;
> > +  typedef decltype(*std::begin(Range)) V;
> > +  return detail::enumerator_impl<I, V>(std::begin(Range),
> std::end(Range));
> > +}
> > +
> >  } // End llvm namespace
> >
> >  #endif
> >
> > Modified: llvm/trunk/unittests/ADT/STLExtrasTest.cpp
> > URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/ADT/STLExtrasTest.cpp?rev=282804&r1=282803&r2=282804&view=diff
> >
> ==============================================================================
> > --- llvm/trunk/unittests/ADT/STLExtrasTest.cpp (original)
> > +++ llvm/trunk/unittests/ADT/STLExtrasTest.cpp Thu Sep 29 17:59:30 2016
> > @@ -10,6 +10,8 @@
> >  #include "llvm/ADT/STLExtras.h"
> >  #include "gtest/gtest.h"
> >
> > +#include <vector>
> > +
> >  using namespace llvm;
> >
> >  namespace {
> > @@ -37,4 +39,51 @@ TEST(STLExtrasTest, Rank) {
> >    EXPECT_EQ(4, f(rank<6>()));
> >  }
> >
> > +TEST(STLExtrasTest, Enumerate) {
> > +  std::vector<char> foo = {'a', 'b', 'c'};
> > +
> > +  std::vector<std::pair<std::size_t, char>> results;
> > +
> > +  for (auto X : llvm::enumerate(foo)) {
> > +    results.push_back(std::make_pair(X.Index, X.Value));
> > +  }
> > +  ASSERT_EQ(3, results.size());
> > +  EXPECT_EQ(0, results[0].first);
> > +  EXPECT_EQ('a', results[0].second);
> > +  EXPECT_EQ(1, results[1].first);
> > +  EXPECT_EQ('b', results[1].second);
> > +  EXPECT_EQ(2, results[2].first);
> > +  EXPECT_EQ('c', results[2].second);
> > +
> > +  results.clear();
> > +  const std::vector<int> bar = {'1', '2', '3'};
> > +  for (auto X : llvm::enumerate(bar)) {
> > +    results.push_back(std::make_pair(X.Index, X.Value));
> > +  }
> > +  EXPECT_EQ(0, results[0].first);
> > +  EXPECT_EQ('1', results[0].second);
> > +  EXPECT_EQ(1, results[1].first);
> > +  EXPECT_EQ('2', results[1].second);
> > +  EXPECT_EQ(2, results[2].first);
> > +  EXPECT_EQ('3', results[2].second);
> > +
> > +  results.clear();
> > +  const std::vector<int> baz;
> > +  for (auto X : llvm::enumerate(baz)) {
> > +    results.push_back(std::make_pair(X.Index, X.Value));
> > +  }
> > +  EXPECT_TRUE(baz.empty());
> > +}
> > +
> > +TEST(STLExtrasTest, EnumerateModify) {
> > +  std::vector<char> foo = {'a', 'b', 'c'};
> > +
> > +  for (auto X : llvm::enumerate(foo)) {
> > +    ++X.Value;
> > +  }
> > +
> > +  EXPECT_EQ('b', foo[0]);
> > +  EXPECT_EQ('c', foo[1]);
> > +  EXPECT_EQ('d', foo[2]);
> > +}
> >  }
> >
> >
> > _______________________________________________
> > llvm-commits mailing list
> > llvm-commits at lists.llvm.org
> > http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20160929/9055ff53/attachment.html>


More information about the llvm-commits mailing list