function-test.c++ (4531B)
1 // Copyright (c) 2013-2014 Sandstorm Development Group, Inc. and contributors 2 // Licensed under the MIT License: 3 // 4 // Permission is hereby granted, free of charge, to any person obtaining a copy 5 // of this software and associated documentation files (the "Software"), to deal 6 // in the Software without restriction, including without limitation the rights 7 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 8 // copies of the Software, and to permit persons to whom the Software is 9 // furnished to do so, subject to the following conditions: 10 // 11 // The above copyright notice and this permission notice shall be included in 12 // all copies or substantial portions of the Software. 13 // 14 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 15 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 16 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 17 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 18 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 19 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 20 // THE SOFTWARE. 21 22 #include "function.h" 23 #include <kj/compat/gtest.h> 24 25 namespace kj { 26 namespace { 27 28 TEST(Function, Lambda) { 29 int i = 0; 30 31 Function<int(int, int)> f = [&](int a, int b) { return a + b + i++; }; 32 33 EXPECT_EQ(123 + 456, f(123, 456)); 34 EXPECT_EQ(7 + 8 + 1, f(7, 8)); 35 EXPECT_EQ(9 + 2 + 2, f(2, 9)); 36 37 EXPECT_EQ(i, 3); 38 } 39 40 struct TestType { 41 int callCount; 42 43 TestType(int callCount = 0): callCount(callCount) {} 44 45 ~TestType() { callCount = 1234; } 46 // Make sure we catch invalid post-destruction uses. 47 48 int foo(int a, int b) { 49 return a + b + callCount++; 50 } 51 52 int foo(int c) { 53 return c * 100; 54 } 55 }; 56 57 TEST(Function, Method) { 58 TestType obj; 59 Function<int(int, int)> f = KJ_BIND_METHOD(obj, foo); 60 Function<uint(uint, uint)> f2 = KJ_BIND_METHOD(obj, foo); 61 62 EXPECT_EQ(123 + 456, f(123, 456)); 63 EXPECT_EQ(7 + 8 + 1, f(7, 8)); 64 EXPECT_EQ(9u + 2u + 2u, f2(2, 9)); 65 66 EXPECT_EQ(3, obj.callCount); 67 68 Function<int(int)> f3 = KJ_BIND_METHOD(obj, foo); 69 EXPECT_EQ(12300, f3(123)); 70 71 // Bind to a temporary. 72 f = KJ_BIND_METHOD(TestType(10), foo); 73 74 EXPECT_EQ(123 + 456 + 10, f(123, 456)); 75 EXPECT_EQ(7 + 8 + 11, f(7, 8)); 76 EXPECT_EQ(9 + 2 + 12, f(2, 9)); 77 78 // Bind to a move. 79 f = KJ_BIND_METHOD(kj::mv(obj), foo); 80 obj.callCount = 1234; 81 82 EXPECT_EQ(123 + 456 + 3, f(123, 456)); 83 EXPECT_EQ(7 + 8 + 4, f(7, 8)); 84 EXPECT_EQ(9 + 2 + 5, f(2, 9)); 85 } 86 87 struct TestConstType { 88 mutable int callCount; 89 90 TestConstType(int callCount = 0): callCount(callCount) {} 91 92 ~TestConstType() { callCount = 1234; } 93 // Make sure we catch invalid post-destruction uses. 94 95 int foo(int a, int b) const { 96 return a + b + callCount++; 97 } 98 }; 99 100 TEST(ConstFunction, Method) { 101 TestConstType obj; 102 ConstFunction<int(int, int)> f = KJ_BIND_METHOD(obj, foo); 103 ConstFunction<uint(uint, uint)> f2 = KJ_BIND_METHOD(obj, foo); 104 105 EXPECT_EQ(123 + 456, f(123, 456)); 106 EXPECT_EQ(7 + 8 + 1, f(7, 8)); 107 EXPECT_EQ(9u + 2u + 2u, f2(2, 9)); 108 109 EXPECT_EQ(3, obj.callCount); 110 111 // Bind to a temporary. 112 f = KJ_BIND_METHOD(TestConstType(10), foo); 113 114 EXPECT_EQ(123 + 456 + 10, f(123, 456)); 115 EXPECT_EQ(7 + 8 + 11, f(7, 8)); 116 EXPECT_EQ(9 + 2 + 12, f(2, 9)); 117 118 // Bind to a move. 119 f = KJ_BIND_METHOD(kj::mv(obj), foo); 120 obj.callCount = 1234; 121 122 EXPECT_EQ(123 + 456 + 3, f(123, 456)); 123 EXPECT_EQ(7 + 8 + 4, f(7, 8)); 124 EXPECT_EQ(9 + 2 + 5, f(2, 9)); 125 } 126 127 int testFunctionParam(FunctionParam<int(char, bool)> func, char c, bool b) { 128 return func(c, b); 129 } 130 131 int testFunctionParamRecursive(FunctionParam<int(char, bool)> func, char c, bool b) { 132 return testFunctionParam(func, c, b); 133 } 134 135 KJ_TEST("FunctionParam") { 136 { 137 int i = 123; 138 int result = testFunctionParam([i](char c, bool b) { 139 KJ_EXPECT(c == 'x'); 140 KJ_EXPECT(b); 141 KJ_EXPECT(i == 123); 142 return 456; 143 }, 'x', true); 144 145 KJ_EXPECT(result == 456); 146 } 147 148 { 149 int i = 123; 150 auto func = [i](char c, bool b) { 151 KJ_EXPECT(c == 'x'); 152 KJ_EXPECT(b); 153 KJ_EXPECT(i == 123); 154 return 456; 155 }; 156 int result = testFunctionParam(func, 'x', true); 157 KJ_EXPECT(result == 456); 158 } 159 160 { 161 int i = 123; 162 int result = testFunctionParamRecursive([i](char c, bool b) { 163 KJ_EXPECT(c == 'x'); 164 KJ_EXPECT(b); 165 KJ_EXPECT(i == 123); 166 return 456; 167 }, 'x', true); 168 169 KJ_EXPECT(result == 456); 170 } 171 } 172 173 } // namespace 174 } // namespace kj