66b987e445d0c9fb65960db9037f10996121181d
[folly.git] / folly / gen / test / BaseTest.cpp
1 /*
2  * Copyright 2016 Facebook, Inc.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *   http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include <glog/logging.h>
18 #include <gtest/gtest.h>
19 #include <iosfwd>
20 #include <random>
21 #include <set>
22 #include <vector>
23
24 #include <folly/FBVector.h>
25 #include <folly/MapUtil.h>
26 #include <folly/Memory.h>
27 #include <folly/String.h>
28 #include <folly/dynamic.h>
29 #include <folly/experimental/TestUtil.h>
30 #include <folly/gen/Base.h>
31
32 using namespace folly::gen;
33 using namespace folly;
34 using std::make_tuple;
35 using std::ostream;
36 using std::pair;
37 using std::set;
38 using std::string;
39 using std::tuple;
40 using std::unique_ptr;
41 using std::vector;
42
43 #define EXPECT_SAME(A, B) \
44   static_assert(std::is_same<A, B>::value, "Mismatched: " #A ", " #B)
45 EXPECT_SAME(int&&, typename ArgumentReference<int>::type);
46 EXPECT_SAME(int&, typename ArgumentReference<int&>::type);
47 EXPECT_SAME(const int&, typename ArgumentReference<const int&>::type);
48 EXPECT_SAME(const int&, typename ArgumentReference<const int>::type);
49
50 template<typename T>
51 ostream& operator<<(ostream& os, const set<T>& values) {
52   return os << from(values);
53 }
54
55 template<typename T>
56 ostream& operator<<(ostream& os, const vector<T>& values) {
57   os << "[";
58   for (auto& value : values) {
59     if (&value != &values.front()) {
60       os << " ";
61     }
62     os << value;
63   }
64   return os << "]";
65 }
66
67 auto square = [](int x) { return x * x; };
68 auto add = [](int a, int b) { return a + b; };
69 auto multiply = [](int a, int b) { return a * b; };
70
71 auto product = foldl(1, multiply);
72
73 template<typename A, typename B>
74 ostream& operator<<(ostream& os, const pair<A, B>& pair) {
75   return os << "(" << pair.first << ", " << pair.second << ")";
76 }
77
78 TEST(Gen, Count) {
79   auto gen = seq(1, 10);
80   EXPECT_EQ(10, gen | count);
81   EXPECT_EQ(5, gen | take(5) | count);
82 }
83
84 TEST(Gen, Sum) {
85   auto gen = seq(1, 10);
86   EXPECT_EQ((1 + 10) * 10 / 2, gen | sum);
87   EXPECT_EQ((1 + 5) * 5 / 2, gen | take(5) | sum);
88 }
89
90 TEST(Gen, Foreach) {
91   auto gen = seq(1, 4);
92   int accum = 0;
93   gen | [&](int x) { accum += x; };
94   EXPECT_EQ(10, accum);
95   int accum2 = 0;
96   gen | take(3) | [&](int x) { accum2 += x; };
97   EXPECT_EQ(6, accum2);
98 }
99
100 TEST(Gen, Map) {
101   auto expected = vector<int>{4, 9, 16};
102   auto gen = from({2, 3, 4}) | map(square);
103   EXPECT_EQ((vector<int>{4, 9, 16}), gen | as<vector>());
104   EXPECT_EQ((vector<int>{4, 9}), gen | take(2) | as<vector>());
105 }
106
107 TEST(Gen, Member) {
108   struct Counter {
109     Counter(int start = 0)
110       : c(start)
111     {}
112
113     int count() const { return c; }
114     int incr() { return ++c; }
115
116     int& ref() { return c; }
117     const int& ref() const { return c; }
118    private:
119     int c;
120   };
121   auto counters = seq(1, 10) | eachAs<Counter>() | as<vector>();
122   EXPECT_EQ(10 * (1 + 10) / 2,
123             from(counters)
124           | member(&Counter::count)
125           | sum);
126   EXPECT_EQ(10 * (1 + 10) / 2,
127             from(counters)
128           | indirect
129           | member(&Counter::count)
130           | sum);
131   EXPECT_EQ(10 * (2 + 11) / 2,
132             from(counters)
133           | member(&Counter::incr)
134           | sum);
135   EXPECT_EQ(10 * (3 + 12) / 2,
136             from(counters)
137           | indirect
138           | member(&Counter::incr)
139           | sum);
140   EXPECT_EQ(10 * (3 + 12) / 2,
141             from(counters)
142           | member(&Counter::count)
143           | sum);
144
145   // type-verifications
146   auto m = empty<Counter&>();
147   auto c = empty<const Counter&>();
148   m | member(&Counter::incr) | assert_type<int&&>();
149   m | member(&Counter::count) | assert_type<int&&>();
150   m | member(&Counter::count) | assert_type<int&&>();
151   m | member<Const>(&Counter::ref) | assert_type<const int&>();
152   m | member<Mutable>(&Counter::ref) | assert_type<int&>();
153   c | member<Const>(&Counter::ref) | assert_type<const int&>();
154 }
155
156 TEST(Gen, Field) {
157   struct X {
158     X() : a(2), b(3), c(4), d(b) {}
159
160     const int a;
161     int b;
162     mutable int c;
163     int& d; // can't access this with a field pointer.
164   };
165
166   std::vector<X> xs(1);
167   EXPECT_EQ(2, from(xs)
168              | field(&X::a)
169              | sum);
170   EXPECT_EQ(3, from(xs)
171              | field(&X::b)
172              | sum);
173   EXPECT_EQ(4, from(xs)
174              | field(&X::c)
175              | sum);
176   EXPECT_EQ(2, seq(&xs[0], &xs[0])
177              | field(&X::a)
178              | sum);
179   // type-verification
180   empty<X&>() | field(&X::a) | assert_type<const int&>();
181   empty<X*>() | field(&X::a) | assert_type<const int&>();
182   empty<X&>() | field(&X::b) | assert_type<int&>();
183   empty<X*>() | field(&X::b) | assert_type<int&>();
184   empty<X&>() | field(&X::c) | assert_type<int&>();
185   empty<X*>() | field(&X::c) | assert_type<int&>();
186
187   empty<X&&>() | field(&X::a) | assert_type<const int&&>();
188   empty<X&&>() | field(&X::b) | assert_type<int&&>();
189   empty<X&&>() | field(&X::c) | assert_type<int&&>();
190   // references don't imply ownership so they're not moved
191
192   empty<const X&>() | field(&X::a) | assert_type<const int&>();
193   empty<const X*>() | field(&X::a) | assert_type<const int&>();
194   empty<const X&>() | field(&X::b) | assert_type<const int&>();
195   empty<const X*>() | field(&X::b) | assert_type<const int&>();
196   // 'mutable' has no effect on field pointers, by C++ spec
197   empty<const X&>() | field(&X::c) | assert_type<const int&>();
198   empty<const X*>() | field(&X::c) | assert_type<const int&>();
199
200   // can't form pointer-to-reference field: empty<X&>() | field(&X::d)
201 }
202
203 TEST(Gen, Seq) {
204   // cover the fenceposts of the loop unrolling
205   for (int n = 1; n < 100; ++n) {
206     EXPECT_EQ(n, seq(1, n) | count);
207     EXPECT_EQ(n + 1, seq(1) | take(n + 1) | count);
208   }
209 }
210
211 TEST(Gen, SeqWithStep) {
212   EXPECT_EQ(75, seq(5, 25, 5) | sum);
213 }
214
215 TEST(Gen, SeqWithStepArray) {
216   const std::array<int, 6> arr{{1, 2, 3, 4, 5, 6}};
217   EXPECT_EQ(9, seq(&arr[0], &arr[5], 2)
218              | map([](const int *i) { return *i; })
219              | sum);
220 }
221
222 TEST(Gen, Range) {
223   // cover the fenceposts of the loop unrolling
224   for (int n = 1; n < 100; ++n) {
225     EXPECT_EQ(gen::range(0, n) | count, n);
226   }
227 }
228
229 TEST(Gen, RangeWithStep) {
230   EXPECT_EQ(50, range(5, 25, 5) | sum);
231 }
232
233 TEST(Gen, FromIterators) {
234   vector<int> source {2, 3, 5, 7, 11};
235   auto gen = from(folly::range(source.begin() + 1, source.end() - 1));
236   EXPECT_EQ(3 * 5 * 7, gen | product);
237 }
238
239 TEST(Gen, FromMap) {
240   auto source = seq(0, 10)
241               | map([](int i) { return std::make_pair(i, i * i); })
242               | as<std::map<int, int>>();
243   auto gen = fromConst(source)
244            | map([&](const std::pair<const int, int>& p) {
245                return p.second - p.first;
246              });
247   EXPECT_EQ(330, gen | sum);
248 }
249
250 TEST(Gen, Filter) {
251   const auto expected = vector<int>{1, 2, 4, 5, 7, 8};
252   auto actual =
253       seq(1, 9)
254     | filter([](int x) { return x % 3; })
255     | as<vector<int>>();
256   EXPECT_EQ(expected, actual);
257 }
258
259 TEST(Gen, FilterDefault) {
260   {
261     // Default filter should remove 0s
262     const auto expected = vector<int>{1, 1, 2, 3};
263     auto actual =
264         from({0, 1, 1, 0, 2, 3, 0})
265       | filter()
266       | as<vector>();
267     EXPECT_EQ(expected, actual);
268   }
269   {
270     // Default filter should remove nullptrs
271     int a = 5;
272     int b = 3;
273     int c = 0;
274     const auto expected = vector<int*>{&a, &b, &c};
275     auto actual =
276         from({(int*)nullptr, &a, &b, &c, (int*)nullptr})
277       | filter()
278       | as<vector>();
279     EXPECT_EQ(expected, actual);
280   }
281   {
282     // Default filter on Optionals should remove folly::null
283     const auto expected =
284         vector<Optional<int>>{Optional<int>(5), Optional<int>(0)};
285     const auto actual =
286         from({Optional<int>(5), Optional<int>(), Optional<int>(0)})
287       | filter()
288       | as<vector>();
289     EXPECT_EQ(expected, actual);
290   }
291 }
292
293 TEST(Gen, FilterSink) {
294   auto actual
295     = seq(1, 2)
296     | map([](int x) { return vector<int>{x}; })
297     | filter([](vector<int> v) { return !v.empty(); })
298     | as<vector>();
299   EXPECT_FALSE(from(actual) | rconcat | isEmpty);
300 }
301
302 TEST(Gen, Contains) {
303   {
304     auto gen =
305         seq(1, 9)
306       | map(square);
307     EXPECT_TRUE(gen | contains(49));
308     EXPECT_FALSE(gen | contains(50));
309   }
310   {
311     auto gen =
312         seq(1) // infinite, to prove laziness
313       | map(square)
314       | eachTo<std::string>();
315
316     // std::string gen, const char* needle
317     EXPECT_TRUE(gen | take(9999) | contains("49"));
318   }
319 }
320
321 TEST(Gen, Take) {
322   {
323     auto expected = vector<int>{1, 4, 9, 16};
324     auto actual =
325       seq(1, 1000)
326       | mapped([](int x) { return x * x; })
327       | take(4)
328       | as<vector<int>>();
329     EXPECT_EQ(expected, actual);
330   }
331   {
332     auto expected = vector<int>{ 0, 1, 4, 5, 8 };
333     auto actual
334       = ((seq(0) | take(2)) +
335          (seq(4) | take(2)) +
336          (seq(8) | take(2)))
337       | take(5)
338       | as<vector>();
339     EXPECT_EQ(expected, actual);
340   }
341   {
342     auto expected = vector<int>{ 0, 1, 4, 5, 8 };
343     auto actual
344       = seq(0)
345       | mapped([](int i) {
346           return seq(i * 4) | take(2);
347         })
348       | concat
349       | take(5)
350       | as<vector>();
351     EXPECT_EQ(expected, actual);
352   }
353   {
354     int64_t limit = 5;
355     take(limit - 5);
356     EXPECT_THROW(take(limit - 6), std::invalid_argument);
357   }
358 }
359
360
361 TEST(Gen, Stride) {
362   {
363     EXPECT_THROW(stride(0), std::invalid_argument);
364   }
365   {
366     auto expected = vector<int>{1, 2, 3, 4};
367     auto actual
368       = seq(1, 4)
369       | stride(1)
370       | as<vector<int>>();
371     EXPECT_EQ(expected, actual);
372   }
373   {
374     auto expected = vector<int>{1, 3, 5, 7};
375     auto actual
376       = seq(1, 8)
377       | stride(2)
378       | as<vector<int>>();
379     EXPECT_EQ(expected, actual);
380   }
381   {
382     auto expected = vector<int>{1, 4, 7, 10};
383     auto actual
384       = seq(1, 12)
385       | stride(3)
386       | as<vector<int>>();
387     EXPECT_EQ(expected, actual);
388   }
389   {
390     auto expected = vector<int>{1, 3, 5, 7, 9, 1, 4, 7, 10};
391     auto actual
392       = ((seq(1, 10) | stride(2)) +
393          (seq(1, 10) | stride(3)))
394       | as<vector<int>>();
395     EXPECT_EQ(expected, actual);
396   }
397   EXPECT_EQ(500, seq(1) | take(1000) | stride(2) | count);
398   EXPECT_EQ(10, seq(1) | take(1000) | stride(2) | take(10) | count);
399 }
400
401 TEST(Gen, Sample) {
402   std::mt19937 rnd(42);
403
404   auto sampler =
405       seq(1, 100)
406     | sample(50, rnd);
407   std::unordered_map<int,int> hits;
408   const int kNumIters = 80;
409   for (int i = 0; i < kNumIters; i++) {
410     auto vec = sampler | as<vector<int>>();
411     EXPECT_EQ(vec.size(), 50);
412     auto uniq = fromConst(vec) | as<set<int>>();
413     EXPECT_EQ(uniq.size(), vec.size());  // sampling without replacement
414     for (auto v: vec) {
415       ++hits[v];
416     }
417   }
418
419   // In 80 separate samples of our range, we should have seen every value
420   // at least once and no value all 80 times. (The odds of either of those
421   // events is 1/2^80).
422   EXPECT_EQ(hits.size(), 100);
423   for (auto hit: hits) {
424     EXPECT_GT(hit.second, 0);
425     EXPECT_LT(hit.second, kNumIters);
426   }
427
428   auto small =
429       seq(1, 5)
430     | sample(10);
431   EXPECT_EQ((small | sum), 15);
432   EXPECT_EQ((small | take(3) | count), 3);
433 }
434
435 TEST(Gen, Skip) {
436   auto gen =
437       seq(1, 1000)
438     | mapped([](int x) { return x * x; })
439     | skip(4)
440     | take(4);
441   EXPECT_EQ((vector<int>{25, 36, 49, 64}), gen | as<vector>());
442 }
443
444 TEST(Gen, Until) {
445   {
446     auto expected = vector<int>{1, 4, 9, 16};
447     auto actual
448       = seq(1, 1000)
449       | mapped([](int x) { return x * x; })
450       | until([](int x) { return x > 20; })
451       | as<vector<int>>();
452     EXPECT_EQ(expected, actual);
453   }
454   {
455     auto expected = vector<int>{ 0, 1, 4, 5, 8 };
456     auto actual
457       = ((seq(0) | until([](int i) { return i > 1; })) +
458          (seq(4) | until([](int i) { return i > 5; })) +
459          (seq(8) | until([](int i) { return i > 9; })))
460       | until([](int i) { return i > 8; })
461       | as<vector<int>>();
462     EXPECT_EQ(expected, actual);
463   }
464   /*
465   {
466     auto expected = vector<int>{ 0, 1, 5, 6, 10 };
467     auto actual
468       = seq(0)
469       | mapped([](int i) {
470           return seq(i * 5) | until([=](int j) { return j > i * 5 + 1; });
471         })
472       | concat
473       | until([](int i) { return i > 10; })
474       | as<vector<int>>();
475     EXPECT_EQ(expected, actual);
476   }
477   */
478 }
479
480 TEST(Gen, Composed) {
481   // Operator, Operator
482   auto valuesOf =
483       filter([](Optional<int>& o) { return o.hasValue(); })
484     | map([](Optional<int>& o) -> int& { return o.value(); });
485   std::vector<Optional<int>> opts {
486     none, 4, none, 6, none
487   };
488   EXPECT_EQ(4 * 4 + 6 * 6, from(opts) | valuesOf | map(square) | sum);
489   // Operator, Sink
490   auto sumOpt = valuesOf | sum;
491   EXPECT_EQ(10, from(opts) | sumOpt);
492 }
493
494 TEST(Gen, Chain) {
495   std::vector<int> nums {2, 3, 5, 7};
496   std::map<int, int> mappings { { 3, 9}, {5, 25} };
497   auto gen = from(nums) + (from(mappings) | get<1>());
498   EXPECT_EQ(51, gen | sum);
499   EXPECT_EQ(5, gen | take(2) | sum);
500   EXPECT_EQ(26, gen | take(5) | sum);
501 }
502
503 TEST(Gen, Concat) {
504   std::vector<std::vector<int>> nums {{2, 3}, {5, 7}};
505   auto gen = from(nums) | rconcat;
506   EXPECT_EQ(17, gen | sum);
507   EXPECT_EQ(10, gen | take(3) | sum);
508 }
509
510 TEST(Gen, ConcatGen) {
511   auto gen = seq(1, 10)
512            | map([](int i) { return seq(1, i); })
513            | concat;
514   EXPECT_EQ(220, gen | sum);
515   EXPECT_EQ(10, gen | take(6) | sum);
516 }
517
518 TEST(Gen, ConcatAlt) {
519   std::vector<std::vector<int>> nums {{2, 3}, {5, 7}};
520   auto actual = from(nums)
521               | map([](std::vector<int>& v) { return from(v); })
522               | concat
523               | sum;
524   auto expected = 17;
525   EXPECT_EQ(expected, actual);
526 }
527
528 TEST(Gen, Order) {
529   auto expected = vector<int>{0, 3, 5, 6, 7, 8, 9};
530   auto actual =
531       from({8, 6, 7, 5, 3, 0, 9})
532     | order
533     | as<vector>();
534   EXPECT_EQ(expected, actual);
535 }
536
537 TEST(Gen, OrderMoved) {
538   auto expected = vector<int>{0, 9, 25, 36, 49, 64, 81};
539   auto actual =
540       from({8, 6, 7, 5, 3, 0, 9})
541     | move
542     | order
543     | map(square)
544     | as<vector>();
545   EXPECT_EQ(expected, actual);
546 }
547
548 TEST(Gen, OrderTake) {
549   auto expected = vector<int>{9, 8, 7};
550   auto actual =
551       from({8, 6, 7, 5, 3, 0, 9})
552     | orderByDescending(square)
553     | take(3)
554     | as<vector>();
555   EXPECT_EQ(expected, actual);
556 }
557
558 TEST(Gen, Distinct) {
559   auto expected = vector<int>{3, 1, 2};
560   auto actual =
561       from({3, 1, 3, 2, 1, 2, 3})
562     | distinct
563     | as<vector>();
564   EXPECT_EQ(expected, actual);
565 }
566
567 TEST(Gen, DistinctBy) {   //  0  1  4  9  6  5  6  9  4  1  0
568   auto expected = vector<int>{0, 1, 2, 3, 4, 5};
569   auto actual =
570       seq(0, 100)
571     | distinctBy([](int i) { return i * i % 10; })
572     | as<vector>();
573   EXPECT_EQ(expected, actual);
574 }
575
576 TEST(Gen, DistinctMove) {   //  0  1  4  9  6  5  6  9  4  1  0
577   auto expected = vector<int>{0, 1, 2, 3, 4, 5};
578   auto actual =
579       seq(0, 100)
580     | mapped([](int i) { return std::unique_ptr<int>(new int(i)); })
581       // see comment below about selector parameters for Distinct
582     | distinctBy([](const std::unique_ptr<int>& pi) { return *pi * *pi % 10; })
583     | mapped([](std::unique_ptr<int> pi) { return *pi; })
584     | as<vector>();
585
586   // NOTE(tjackson): the following line intentionally doesn't work:
587   //  | distinctBy([](std::unique_ptr<int> pi) { return *pi * *pi % 10; })
588   // This is because distinctBy because the selector intentionally requires a
589   // const reference.  If it required a move-reference, the value might get
590   // gutted by the selector before said value could be passed to downstream
591   // operators.
592   EXPECT_EQ(expected, actual);
593 }
594
595 TEST(Gen, DistinctInfinite) {
596   // distinct should be able to handle an infinite sequence, provided that, of
597   // of cource, is it eventually made finite before returning the result.
598   auto expected = seq(0) | take(5) | as<vector>(); // 0 1 2 3 4
599
600   auto actual =
601       seq(0)                              // 0 1 2 3 4 5 6 7 ...
602     | mapped([](int i) { return i / 2; }) // 0 0 1 1 2 2 3 3 ...
603     | distinct                            // 0 1 2 3 4 5 6 7 ...
604     | take(5)                             // 0 1 2 3 4
605     | as<vector>();
606
607   EXPECT_EQ(expected, actual);
608 }
609
610 TEST(Gen, DistinctByInfinite) {
611   // Similarly to the DistinctInfinite test case, distinct by should be able to
612   // handle infinite sequences. Note that depending on how many values we take()
613   // at the end, the sequence may infinite loop. This is fine becasue we cannot
614   // solve the halting problem.
615   auto expected = vector<int>{1, 2};
616   auto actual =
617       seq(1)                                    // 1 2 3 4 5 6 7 8 ...
618     | distinctBy([](int i) { return i % 2; })   // 1 2 (but might by infinite)
619     | take(2)                                   // 1 2
620     | as<vector>();
621   // Note that if we had take(3), this would infinite loop
622
623   EXPECT_EQ(expected, actual);
624 }
625
626 TEST(Gen, MinBy) {
627   EXPECT_EQ(7, seq(1, 10)
628              | minBy([](int i) -> double {
629                  double d = i - 6.8;
630                  return d * d;
631                })
632              | unwrap);
633 }
634
635 TEST(Gen, MaxBy) {
636   auto gen = from({"three", "eleven", "four"});
637
638   EXPECT_EQ("eleven", gen | maxBy(&strlen) | unwrap);
639 }
640
641 TEST(Gen, Min) {
642   auto odds = seq(2,10) | filter([](int i){ return i % 2; });
643
644   EXPECT_EQ(3, odds | min);
645 }
646
647 TEST(Gen, Max) {
648   auto odds = seq(2,10) | filter([](int i){ return i % 2; });
649
650   EXPECT_EQ(9, odds | max);
651 }
652
653 TEST(Gen, Append) {
654   string expected = "facebook";
655   string actual = "face";
656   from(StringPiece("book")) | appendTo(actual);
657   EXPECT_EQ(expected, actual);
658 }
659
660 TEST(Gen, FromRValue) {
661   {
662     // AFAICT The C++ Standard does not specify what happens to the rvalue
663     // reference of a std::vector when it is used as the 'other' for an rvalue
664     // constructor.  Use fbvector because we're sure its size will be zero in
665     // this case.
666     fbvector<int> v({1,2,3,4});
667     auto q1 = from(v);
668     EXPECT_EQ(v.size(), 4);  // ensure that the lvalue version was called!
669     auto expected = 1 * 2 * 3 * 4;
670     EXPECT_EQ(expected, q1 | product);
671
672     auto q2 = from(std::move(v));
673     EXPECT_EQ(v.size(), 0);  // ensure that rvalue version was called
674     EXPECT_EQ(expected, q2 | product);
675   }
676   {
677     auto expected = 7;
678     auto q = from([] {return vector<int>({3,7,5}); }());
679     EXPECT_EQ(expected, q | max);
680   }
681   {
682     for (auto size: {5, 1024, 16384, 1<<20}) {
683       auto q1 = from(vector<int>(size, 2));
684       auto q2 = from(vector<int>(size, 3));
685       // If the rvalue specialization is broken/gone, then the compiler will
686       // (disgustingly!) just store a *reference* to the temporary object,
687       // which is bad.  Try to catch this by allocating two temporary vectors
688       // of the same size, so that they'll probably use the same underlying
689       // buffer if q1's vector is destructed before q2's vector is constructed.
690       EXPECT_EQ(size * 2 + size * 3, (q1 | sum) + (q2 | sum));
691     }
692   }
693   {
694     auto q = from(set<int>{1,2,3,2,1});
695     EXPECT_EQ(q | sum, 6);
696   }
697 }
698
699 TEST(Gen, OrderBy) {
700   auto expected = vector<int>{5, 6, 4, 7, 3, 8, 2, 9, 1, 10};
701   auto actual =
702       seq(1, 10)
703     | orderBy([](int x) { return (5.1 - x) * (5.1 - x); })
704     | as<vector>();
705   EXPECT_EQ(expected, actual);
706
707   expected = seq(1, 10) | as<vector>();
708   actual =
709       from(expected)
710     | map([] (int x) { return 11 - x; })
711     | orderBy()
712     | as<vector>();
713   EXPECT_EQ(expected, actual);
714 }
715
716 TEST(Gen, Foldl) {
717   int expected = 2 * 3 * 4 * 5;
718   auto actual =
719       seq(2, 5)
720     | foldl(1, multiply);
721   EXPECT_EQ(expected, actual);
722 }
723
724 TEST(Gen, Reduce) {
725   int expected = 2 + 3 + 4 + 5;
726   auto actual = seq(2, 5) | reduce(add);
727   EXPECT_EQ(expected, actual | unwrap);
728 }
729
730 TEST(Gen, ReduceBad) {
731   auto gen = seq(1) | take(0);
732   auto actual = gen | reduce(add);
733   EXPECT_FALSE(actual); // Empty sequences are okay, they just yeild 'none'
734 }
735
736 TEST(Gen, Moves) {
737   std::vector<unique_ptr<int>> ptrs;
738   ptrs.emplace_back(new int(1));
739   EXPECT_NE(ptrs.front().get(), nullptr);
740   auto ptrs2 = from(ptrs) | move | as<vector>();
741   EXPECT_EQ(ptrs.front().get(), nullptr);
742   EXPECT_EQ(**ptrs2.data(), 1);
743 }
744
745 TEST(Gen, First) {
746   auto gen = seq(0) | filter([](int x) { return x > 3; });
747   EXPECT_EQ(4, gen | first | unwrap);
748 }
749
750 TEST(Gen, FromCopy) {
751   vector<int> v {3, 5};
752   auto src = from(v);
753   auto copy = fromCopy(v);
754   EXPECT_EQ(8, src | sum);
755   EXPECT_EQ(8, copy | sum);
756   v[1] = 7;
757   EXPECT_EQ(10, src | sum);
758   EXPECT_EQ(8, copy | sum);
759 }
760
761 TEST(Gen, Get) {
762   std::map<int, int> pairs {
763     {1, 1},
764     {2, 4},
765     {3, 9},
766     {4, 16},
767   };
768   auto pairSrc = from(pairs);
769   auto keys = pairSrc | get<0>();
770   auto values = pairSrc | get<1>();
771   EXPECT_EQ(10, keys | sum);
772   EXPECT_EQ(30, values | sum);
773   EXPECT_EQ(30, keys | map(square) | sum);
774   pairs[5] = 25;
775   EXPECT_EQ(15, keys | sum);
776   EXPECT_EQ(55, values | sum);
777
778   vector<tuple<int, int, int>> tuples {
779     make_tuple(1, 1, 1),
780     make_tuple(2, 4, 8),
781     make_tuple(3, 9, 27),
782   };
783   EXPECT_EQ(36, from(tuples) | get<2>() | sum);
784 }
785
786 TEST(Gen, notEmpty) {
787   EXPECT_TRUE(seq(0, 1) | notEmpty);
788   EXPECT_TRUE(just(1) | notEmpty);
789   EXPECT_FALSE(gen::range(0, 0) | notEmpty);
790   EXPECT_FALSE(from({1}) | take(0) | notEmpty);
791 }
792
793 TEST(Gen, isEmpty) {
794   EXPECT_FALSE(seq(0, 1) | isEmpty);
795   EXPECT_FALSE(just(1) | isEmpty);
796   EXPECT_TRUE(gen::range(0, 0) | isEmpty);
797   EXPECT_TRUE(from({1}) | take(0) | isEmpty);
798 }
799
800 TEST(Gen, Any) {
801   EXPECT_TRUE(seq(0, 10) | any([](int i) { return i == 7; }));
802   EXPECT_FALSE(seq(0, 10) | any([](int i) { return i == 11; }));
803 }
804
805 TEST(Gen, All) {
806   EXPECT_TRUE(seq(0, 10) | all([](int i) { return i < 11; }));
807   EXPECT_FALSE(seq(0, 10) | all([](int i) { return i < 5; }));
808   EXPECT_FALSE(seq(0) | take(9999) | all([](int i) { return i < 10; }));
809
810   // empty lists satisfies all
811   EXPECT_TRUE(seq(0) | take(0) | all([](int i) { return i < 50; }));
812   EXPECT_TRUE(seq(0) | take(0) | all([](int i) { return i > 50; }));
813 }
814
815 TEST(Gen, Yielders) {
816   auto gen = GENERATOR(int) {
817     for (int i = 1; i <= 5; ++i) {
818       yield(i);
819     }
820     yield(7);
821     for (int i = 3; ; ++i) {
822       yield(i * i);
823     }
824   };
825   vector<int> expected {
826     1, 2, 3, 4, 5, 7, 9, 16, 25
827   };
828   EXPECT_EQ(expected, gen | take(9) | as<vector>());
829 }
830
831 TEST(Gen, NestedYield) {
832   auto nums = GENERATOR(int) {
833     for (int i = 1; ; ++i) {
834       yield(i);
835     }
836   };
837   auto gen = GENERATOR(int) {
838     nums | take(10) | yield;
839     seq(1, 5) | [&](int i) {
840       yield(i);
841     };
842   };
843   EXPECT_EQ(70, gen | sum);
844 }
845
846 TEST(Gen, MapYielders) {
847   auto gen = seq(1, 5)
848            | map([](int n) {
849                return GENERATOR(int) {
850                  int i;
851                  for (i = 1; i < n; ++i)
852                    yield(i);
853                  for (; i >= 1; --i)
854                    yield(i);
855                };
856              })
857            | concat;
858   vector<int> expected {
859                 1,
860              1, 2, 1,
861           1, 2, 3, 2, 1,
862        1, 2, 3, 4, 3, 2, 1,
863     1, 2, 3, 4, 5, 4, 3, 2, 1,
864   };
865   EXPECT_EQ(expected, gen | as<vector>());
866 }
867
868 TEST(Gen, VirtualGen) {
869   VirtualGen<int> v(seq(1, 10));
870   EXPECT_EQ(55, v | sum);
871   v = v | map(square);
872   EXPECT_EQ(385, v | sum);
873   v = v | take(5);
874   EXPECT_EQ(55, v | sum);
875   EXPECT_EQ(30, v | take(4) | sum);
876 }
877
878
879 TEST(Gen, CustomType) {
880   struct Foo{
881     int y;
882   };
883   auto gen = from({Foo{2}, Foo{3}})
884            | map([](const Foo& f) { return f.y; });
885   EXPECT_EQ(5, gen | sum);
886 }
887
888 TEST(Gen, NoNeedlessCopies) {
889   auto gen = seq(1, 5)
890            | map([](int x) { return unique_ptr<int>(new int(x)); })
891            | map([](unique_ptr<int> p) { return p; })
892            | map([](unique_ptr<int>&& p) { return std::move(p); })
893            | map([](const unique_ptr<int>& p) { return *p; });
894   EXPECT_EQ(15, gen | sum);
895   EXPECT_EQ(6, gen | take(3) | sum);
896 }
897
898 namespace {
899
900 class TestIntSeq : public GenImpl<int, TestIntSeq> {
901  public:
902   TestIntSeq() { }
903
904   template <class Body>
905   bool apply(Body&& body) const {
906     for (int i = 1; i < 6; ++i) {
907       if (!body(i)) {
908         return false;
909       }
910     }
911     return true;
912   }
913
914   TestIntSeq(TestIntSeq&&) noexcept = default;
915   TestIntSeq& operator=(TestIntSeq&&) noexcept = default;
916   TestIntSeq(const TestIntSeq&) = delete;
917   TestIntSeq& operator=(const TestIntSeq&) = delete;
918 };
919
920 }  // namespace
921
922 TEST(Gen, NoGeneratorCopies) {
923   EXPECT_EQ(15, TestIntSeq() | sum);
924   auto x = TestIntSeq() | take(3);
925   EXPECT_EQ(6, std::move(x) | sum);
926 }
927
928 TEST(Gen, FromArray) {
929   int source[] = {2, 3, 5, 7};
930   auto gen = from(source);
931   EXPECT_EQ(2 * 3 * 5 * 7, gen | product);
932 }
933
934 TEST(Gen, FromStdArray) {
935   std::array<int,4> source {{2, 3, 5, 7}};
936   auto gen = from(source);
937   EXPECT_EQ(2 * 3 * 5 * 7, gen | product);
938 }
939
940 TEST(Gen, StringConcat) {
941   auto gen = seq(1, 10)
942            | eachTo<string>()
943            | rconcat;
944   EXPECT_EQ("12345678910", gen | as<string>());
945 }
946
947 struct CopyCounter {
948   static int alive;
949   int copies;
950   int moves;
951
952   CopyCounter() : copies(0), moves(0) {
953     ++alive;
954   }
955
956   CopyCounter(CopyCounter&& source) noexcept {
957     *this = std::move(source);
958     ++alive;
959   }
960
961   CopyCounter(const CopyCounter& source) {
962     *this = source;
963     ++alive;
964   }
965
966   ~CopyCounter() {
967     --alive;
968   }
969
970   CopyCounter& operator=(const CopyCounter& source) {
971     this->copies = source.copies + 1;
972     this->moves = source.moves;
973     return *this;
974   }
975
976   CopyCounter& operator=(CopyCounter&& source) {
977     this->copies = source.copies;
978     this->moves = source.moves + 1;
979     return *this;
980   }
981 };
982
983 int CopyCounter::alive = 0;
984
985 TEST(Gen, CopyCount) {
986   vector<CopyCounter> originals;
987   originals.emplace_back();
988   EXPECT_EQ(1, originals.size());
989   EXPECT_EQ(0, originals.back().copies);
990
991   vector<CopyCounter> copies = from(originals) | as<vector>();
992   EXPECT_EQ(1, copies.back().copies);
993   EXPECT_EQ(0, copies.back().moves);
994
995   vector<CopyCounter> moves = from(originals) | move | as<vector>();
996   EXPECT_EQ(0, moves.back().copies);
997   EXPECT_EQ(1, moves.back().moves);
998 }
999
1000 // test dynamics with various layers of nested arrays.
1001 TEST(Gen, Dynamic) {
1002   dynamic array1 = dynamic::array(1, 2);
1003   EXPECT_EQ(dynamic(3), from(array1) | sum);
1004   dynamic array2 = {{1}, {1, 2}};
1005   EXPECT_EQ(dynamic(4), from(array2) | rconcat | sum);
1006   dynamic array3 = {{{1}}, {{1}, {1, 2}}};
1007   EXPECT_EQ(dynamic(5), from(array3) | rconcat | rconcat | sum);
1008 }
1009
1010 TEST(Gen, DynamicObject) {
1011   const dynamic obj = dynamic::object(1, 2)(3, 4);
1012   EXPECT_EQ(dynamic(4), from(obj.keys()) | sum);
1013   EXPECT_EQ(dynamic(6), from(obj.values()) | sum);
1014   EXPECT_EQ(dynamic(4), from(obj.items()) | get<0>() | sum);
1015   EXPECT_EQ(dynamic(6), from(obj.items()) | get<1>() | sum);
1016 }
1017
1018 TEST(Gen, Collect) {
1019   auto s = from({7, 6, 5, 4, 3}) | as<set<int>>();
1020   EXPECT_EQ(s.size(), 5);
1021 }
1022
1023
1024 TEST(Gen, Cycle) {
1025   {
1026     auto s = from({1, 2});
1027     EXPECT_EQ((vector<int> { 1, 2, 1, 2, 1 }),
1028               s | cycle | take(5) | as<vector>());
1029   }
1030   {
1031     auto s = from({1, 2});
1032     EXPECT_EQ((vector<int> { 1, 2, 1, 2 }),
1033               s | cycle(2) | as<vector>());
1034   }
1035   {
1036     auto s = from({1, 2, 3});
1037     EXPECT_EQ((vector<int> { 1, 2, 1, 2, 1 }),
1038               s | take(2) | cycle | take(5) | as<vector>());
1039   }
1040   {
1041     auto s = empty<int>();
1042     EXPECT_EQ((vector<int> { }),
1043               s | cycle | take(4) | as<vector>());
1044   }
1045   {
1046     int count = 3;
1047     int* pcount = &count;
1048     auto countdown = GENERATOR(int) {
1049       ASSERT_GE(*pcount, 0)
1050         << "Cycle should have stopped when it didnt' get values!";
1051       for (int i = 1; i <= *pcount; ++i) {
1052         yield(i);
1053       }
1054       --*pcount;
1055     };
1056     auto s = countdown;
1057     EXPECT_EQ((vector<int> { 1, 2, 3, 1, 2, 1}),
1058               s | cycle | take(7) | as<vector>());
1059     // take necessary as cycle returns an infinite generator
1060   }
1061 }
1062
1063 TEST(Gen, Dereference) {
1064   {
1065     const int x = 4, y = 2;
1066     auto s = from(std::initializer_list<const int*>({&x, nullptr, &y}));
1067     EXPECT_EQ(6, s | dereference | sum);
1068   }
1069   {
1070     vector<int> a { 1, 2 };
1071     vector<int> b { 3, 4 };
1072     vector<vector<int>*> pv { &a, nullptr, &b };
1073     from(pv)
1074       | dereference
1075       | [&](vector<int>& v) {
1076           v.push_back(5);
1077         };
1078     EXPECT_EQ(3, a.size());
1079     EXPECT_EQ(3, b.size());
1080     EXPECT_EQ(5, a.back());
1081     EXPECT_EQ(5, b.back());
1082   }
1083   {
1084     vector<std::map<int, int>> maps {
1085       {
1086         { 2, 31 },
1087         { 3, 41 },
1088       },
1089       {
1090         { 3, 52 },
1091         { 4, 62 },
1092       },
1093       {
1094         { 4, 73 },
1095         { 5, 83 },
1096       },
1097     };
1098     EXPECT_EQ(
1099       93,
1100       from(maps)
1101       | map([](std::map<int, int>& m) {
1102           return get_ptr(m, 3);
1103         })
1104       | dereference
1105       | sum);
1106   }
1107   {
1108     vector<unique_ptr<int>> ups;
1109     ups.emplace_back(new int(3));
1110     ups.emplace_back();
1111     ups.emplace_back(new int(7));
1112     EXPECT_EQ(10, from(ups) | dereference | sum);
1113     EXPECT_EQ(10, from(ups) | move | dereference | sum);
1114   }
1115 }
1116
1117 namespace {
1118 struct DereferenceWrapper {
1119   string data;
1120   string& operator*() & {
1121     return data;
1122   }
1123   string&& operator*() && {
1124     return std::move(data);
1125   }
1126   explicit operator bool() {
1127     return true;
1128   }
1129 };
1130 bool operator==(const DereferenceWrapper& a, const DereferenceWrapper& b) {
1131   return a.data == b.data;
1132 }
1133 void PrintTo(const DereferenceWrapper& a, std::ostream* o) {
1134   *o << "Wrapper{\"" << cEscape<string>(a.data) << "\"}";
1135 }
1136 }
1137
1138 TEST(Gen, DereferenceWithLValueRef) {
1139   auto original = vector<DereferenceWrapper>{{"foo"}, {"bar"}};
1140   auto copy = original;
1141   auto expected = vector<string>{"foo", "bar"};
1142   auto actual = from(original) | dereference | as<vector>();
1143   EXPECT_EQ(expected, actual);
1144   EXPECT_EQ(copy, original);
1145 }
1146
1147 TEST(Gen, DereferenceWithRValueRef) {
1148   auto original = vector<DereferenceWrapper>{{"foo"}, {"bar"}};
1149   auto empty = vector<DereferenceWrapper>{{}, {}};
1150   auto expected = vector<string>{"foo", "bar"};
1151   auto actual = from(original) | move | dereference | as<vector>();
1152   EXPECT_EQ(expected, actual);
1153   EXPECT_EQ(empty, original);
1154 }
1155
1156 TEST(Gen, Indirect) {
1157   vector<int> vs{1};
1158   EXPECT_EQ(&vs[0], from(vs) | indirect | first | unwrap);
1159 }
1160
1161 TEST(Gen, Guard) {
1162   using std::runtime_error;
1163   EXPECT_THROW(from({"1", "a", "3"})
1164                | eachTo<int>()
1165                | sum,
1166                runtime_error);
1167   EXPECT_EQ(4,
1168             from({"1", "a", "3"})
1169             | guard<runtime_error>([](runtime_error&, const char*) {
1170                 return true; // continue
1171               })
1172             | eachTo<int>()
1173             | sum);
1174   EXPECT_EQ(1,
1175             from({"1", "a", "3"})
1176             | guard<runtime_error>([](runtime_error&, const char*) {
1177                 return false; // break
1178               })
1179             | eachTo<int>()
1180             | sum);
1181   EXPECT_THROW(from({"1", "a", "3"})
1182                 | guard<runtime_error>([](runtime_error&, const char* v) {
1183                     if (v[0] == 'a') {
1184                       throw;
1185                     }
1186                     return true;
1187                   })
1188                | eachTo<int>()
1189                | sum,
1190                runtime_error);
1191 }
1192
1193 TEST(Gen, Batch) {
1194   EXPECT_EQ((vector<vector<int>> { {1} }),
1195             seq(1, 1) | batch(5) | as<vector>());
1196   EXPECT_EQ((vector<vector<int>> { {1, 2, 3}, {4, 5, 6}, {7, 8, 9}, {10, 11} }),
1197             seq(1, 11) | batch(3) | as<vector>());
1198   EXPECT_THROW(seq(1, 1) | batch(0) | as<vector>(),
1199                std::invalid_argument);
1200 }
1201
1202 TEST(Gen, BatchMove) {
1203   auto expected = vector<vector<int>>{ {0, 1}, {2, 3}, {4} };
1204   auto actual =
1205       seq(0, 4)
1206     | mapped([](int i) { return std::unique_ptr<int>(new int(i)); })
1207     | batch(2)
1208     | mapped([](std::vector<std::unique_ptr<int>>& pVector) {
1209         std::vector<int> iVector;
1210         for (const auto& p : pVector) {
1211           iVector.push_back(*p);
1212         };
1213         return iVector;
1214       })
1215     | as<vector>();
1216   EXPECT_EQ(expected, actual);
1217 }
1218
1219 TEST(Gen, Just) {
1220   {
1221     int x = 3;
1222     auto j = just(x);
1223     EXPECT_EQ(&x, j | indirect | first | unwrap);
1224     x = 4;
1225     EXPECT_EQ(4, j | sum);
1226   }
1227   {
1228     int x = 3;
1229     const int& cx = x;
1230     auto j = just(cx);
1231     EXPECT_EQ(&x, j | indirect | first | unwrap);
1232     x = 5;
1233     EXPECT_EQ(5, j | sum);
1234   }
1235   {
1236     int x = 3;
1237     auto j = just(std::move(x));
1238     EXPECT_NE(&x, j | indirect | first | unwrap);
1239     x = 5;
1240     EXPECT_EQ(3, j | sum);
1241   }
1242 }
1243
1244 TEST(Gen, GroupBy) {
1245   vector<string> strs{"zero", "one", "two",   "three", "four",
1246                       "five", "six", "seven", "eight", "nine"};
1247
1248   auto gb = from(strs) | groupBy([](const string& str) { return str.size(); });
1249
1250   EXPECT_EQ(10, gb | mapOp(count) | sum);
1251   EXPECT_EQ(3, gb | count);
1252
1253   vector<string> mode{"zero", "four", "five", "nine"};
1254   EXPECT_EQ(mode,
1255             gb | maxBy([](const Group<size_t, string>& g) { return g.size(); })
1256                | unwrap
1257                | as<vector>());
1258
1259   vector<string> largest{"three", "seven", "eight"};
1260   EXPECT_EQ(largest,
1261             gb | maxBy([](const Group<size_t, string>& g) { return g.key(); })
1262                | unwrap
1263                | as<vector>());
1264 }
1265
1266 TEST(Gen, Unwrap) {
1267   Optional<int> o(4);
1268   Optional<int> e;
1269   EXPECT_EQ(4, o | unwrap);
1270   EXPECT_THROW(e | unwrap, OptionalEmptyException);
1271
1272   auto oup = folly::make_optional(folly::make_unique<int>(5));
1273   // optional has a value, and that value is non-null
1274   EXPECT_TRUE(bool(oup | unwrap));
1275   EXPECT_EQ(5, *(oup | unwrap));
1276   EXPECT_TRUE(oup.hasValue()); // still has a pointer (null or not)
1277   EXPECT_TRUE(bool(oup.value())); // that value isn't null
1278
1279   auto moved1 = std::move(oup) | unwrapOr(folly::make_unique<int>(6));
1280   // oup still has a value, but now it's now nullptr since the pointer was moved
1281   // into moved1
1282   EXPECT_TRUE(oup.hasValue());
1283   EXPECT_FALSE(oup.value());
1284   EXPECT_TRUE(bool(moved1));
1285   EXPECT_EQ(5, *moved1);
1286
1287   auto moved2 = std::move(oup) | unwrapOr(folly::make_unique<int>(7));
1288   // oup's still-valid nullptr value wins here, the pointer to 7 doesn't apply
1289   EXPECT_FALSE(moved2);
1290
1291   oup.clear();
1292   auto moved3 = std::move(oup) | unwrapOr(folly::make_unique<int>(8));
1293   // oup is empty now, so the unwrapOr comes into play.
1294   EXPECT_TRUE(bool(moved3));
1295   EXPECT_EQ(8, *moved3);
1296
1297   {
1298   // mixed types, with common type matching optional
1299     Optional<double> full(3.3);
1300     decltype(full) empty;
1301     auto fallback = unwrapOr(4);
1302     EXPECT_EQ(3.3, full | fallback);
1303     EXPECT_EQ(3.3, std::move(full) | fallback);
1304     EXPECT_EQ(3.3, full | std::move(fallback));
1305     EXPECT_EQ(3.3, std::move(full) | std::move(fallback));
1306     EXPECT_EQ(4.0, empty | fallback);
1307     EXPECT_EQ(4.0, std::move(empty) | fallback);
1308     EXPECT_EQ(4.0, empty | std::move(fallback));
1309     EXPECT_EQ(4.0, std::move(empty) | std::move(fallback));
1310   }
1311
1312   {
1313   // mixed types, with common type matching fallback
1314     Optional<int> full(3);
1315     decltype(full) empty;
1316     auto fallback = unwrapOr(5.0); // type: double
1317     // if we chose 'int' as the common type, we'd see truncation here
1318     EXPECT_EQ(1.5, (full | fallback) / 2);
1319     EXPECT_EQ(1.5, (std::move(full) | fallback) / 2);
1320     EXPECT_EQ(1.5, (full | std::move(fallback)) / 2);
1321     EXPECT_EQ(1.5, (std::move(full) | std::move(fallback)) / 2);
1322     EXPECT_EQ(2.5, (empty | fallback) / 2);
1323     EXPECT_EQ(2.5, (std::move(empty) | fallback) / 2);
1324     EXPECT_EQ(2.5, (empty | std::move(fallback)) / 2);
1325     EXPECT_EQ(2.5, (std::move(empty) | std::move(fallback)) / 2);
1326   }
1327
1328   {
1329     auto opt = folly::make_optional(std::make_shared<int>(8));
1330     auto fallback = unwrapOr(folly::make_unique<int>(9));
1331     // fallback must be std::move'd to be used
1332     EXPECT_EQ(8, *(opt | std::move(fallback)));
1333     EXPECT_TRUE(bool(opt.value())); // shared_ptr copied out, not moved
1334     EXPECT_TRUE(bool(opt)); // value still present
1335     EXPECT_TRUE(bool(fallback.value())); // fallback value not needed
1336
1337     EXPECT_EQ(8, *(std::move(opt) | std::move(fallback)));
1338     EXPECT_FALSE(opt.value()); // shared_ptr moved out
1339     EXPECT_TRUE(bool(opt)); // gutted value still present
1340     EXPECT_TRUE(bool(fallback.value())); // fallback value not needed
1341
1342     opt.clear();
1343
1344     EXPECT_FALSE(opt); // opt is empty now
1345     EXPECT_EQ(9, *(std::move(opt) | std::move(fallback)));
1346     EXPECT_FALSE(fallback.value()); // fallback moved out!
1347   }
1348
1349   {
1350     // test with nullptr
1351     vector<int> v{1, 2};
1352     EXPECT_EQ(&v[1], from(v) | indirect | max | unwrap);
1353     v.clear();
1354     EXPECT_FALSE(from(v) | indirect | max | unwrapOr(nullptr));
1355   }
1356
1357   {
1358     // mixed type determined by fallback
1359     Optional<std::nullptr_t> empty;
1360     int x = 3;
1361     EXPECT_EQ(&x, empty | unwrapOr(&x));
1362   }
1363 }
1364
1365 int main(int argc, char *argv[]) {
1366   testing::InitGoogleTest(&argc, argv);
1367   gflags::ParseCommandLineFlags(&argc, &argv, true);
1368   return RUN_ALL_TESTS();
1369 }