1// Test for range-based for loop with templates 2// and begin/end as member functions 3 4// { dg-do run { target c++11 } } 5 6/* Preliminary declarations */ 7namespace pre 8{ 9 struct iterator 10 { 11 int x; 12 explicit iterator (int v) :x(v) {} 13 iterator &operator ++() { ++x; return *this; } 14 int operator *() { return x; } 15 bool operator != (const iterator &o) { return x != o.x; } 16 }; 17 18 struct container 19 { 20 int min, max; 21 container(int a, int b) :min(a), max(b) {} 22 iterator begin() const 23 { 24 return iterator(min); 25 } 26 iterator end() const 27 { 28 return iterator(max); 29 } 30 31 }; 32 33} //namespace pre 34 35using pre::container; 36extern "C" void abort(void); 37 38container run_me_just_once() 39{ 40 static bool run = false; 41 if (run) 42 abort(); 43 run = true; 44 return container(1,2); 45} 46 47/* Template with dependent expression. */ 48template<typename T> int test1(const T &r) 49{ 50 int t = 0; 51 for (int i : r) 52 t += i; 53 return t; 54} 55 56/* Template with non-dependent expression and dependent declaration. */ 57template<typename T> int test2(const container &r) 58{ 59 int t = 0; 60 for (T i : r) 61 t += i; 62 return t; 63} 64 65/* Template with non-dependent expression (array) and dependent declaration. */ 66template<typename T> int test2(const int (&r)[4]) 67{ 68 int t = 0; 69 for (T i : r) 70 t += i; 71 return t; 72} 73 74/* Template with non-dependent expression and auto declaration. */ 75template<typename T> int test3(const container &r) 76{ 77 int t = 0; 78 for (auto i : r) 79 t += i; 80 return t; 81} 82 83/* Template with non-dependent expression (array) and auto declaration. */ 84template<typename T> int test3(const int (&r)[4]) 85{ 86 int t = 0; 87 for (auto i : r) 88 t += i; 89 return t; 90} 91 92int main () 93{ 94 container c(1,5); 95 int a[4] = {5,6,7,8}; 96 97 for (auto x : run_me_just_once()) 98 ; 99 100 if (test1 (c) != 10) 101 abort(); 102 if (test1 (a) != 26) 103 abort(); 104 105 if (test2<int> (c) != 10) 106 abort(); 107 if (test2<int> (a) != 26) 108 abort(); 109 110 if (test3<int> (c) != 10) 111 abort(); 112 if (test3<int> (a) != 26) 113 abort(); 114 return 0; 115} 116