rice 4.0.4 → 4.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +37 -0
- data/CONTRIBUTORS.md +2 -0
- data/Rakefile +1 -1
- data/include/rice/rice.hpp +2851 -1955
- data/include/rice/stl.hpp +1654 -287
- data/lib/mkmf-rice.rb +5 -2
- data/lib/version.rb +1 -1
- data/rice/Arg.hpp +6 -6
- data/rice/Arg.ipp +8 -9
- data/rice/Constructor.hpp +2 -2
- data/rice/Data_Object.ipp +69 -15
- data/rice/Data_Object_defn.hpp +1 -15
- data/rice/Data_Type.ipp +56 -86
- data/rice/Data_Type_defn.hpp +14 -17
- data/rice/Director.hpp +0 -1
- data/rice/Enum.ipp +31 -22
- data/rice/Exception.ipp +2 -3
- data/rice/Exception_defn.hpp +5 -5
- data/rice/HandlerRegistration.hpp +15 -0
- data/rice/Return.hpp +5 -4
- data/rice/Return.ipp +8 -3
- data/rice/detail/ExceptionHandler.hpp +8 -0
- data/rice/detail/ExceptionHandler.ipp +28 -0
- data/rice/detail/{Exception_Handler_defn.hpp → ExceptionHandler_defn.hpp} +17 -21
- data/rice/detail/HandlerRegistry.hpp +51 -0
- data/rice/detail/HandlerRegistry.ipp +20 -0
- data/rice/detail/InstanceRegistry.hpp +34 -0
- data/rice/detail/InstanceRegistry.ipp +50 -0
- data/rice/detail/MethodInfo.ipp +1 -1
- data/rice/detail/NativeAttribute.hpp +26 -15
- data/rice/detail/NativeAttribute.ipp +76 -47
- data/rice/detail/NativeFunction.hpp +64 -14
- data/rice/detail/NativeFunction.ipp +138 -86
- data/rice/detail/NativeIterator.hpp +49 -0
- data/rice/detail/NativeIterator.ipp +102 -0
- data/rice/detail/NativeRegistry.hpp +31 -0
- data/rice/detail/{method_data.ipp → NativeRegistry.ipp} +20 -16
- data/rice/detail/Registries.hpp +26 -0
- data/rice/detail/Registries.ipp +23 -0
- data/rice/detail/RubyFunction.hpp +6 -11
- data/rice/detail/RubyFunction.ipp +10 -22
- data/rice/detail/Type.hpp +1 -1
- data/rice/detail/Type.ipp +2 -2
- data/rice/detail/TypeRegistry.hpp +8 -11
- data/rice/detail/TypeRegistry.ipp +3 -28
- data/rice/detail/Wrapper.hpp +0 -2
- data/rice/detail/Wrapper.ipp +74 -24
- data/rice/detail/cpp_protect.hpp +93 -0
- data/rice/detail/default_allocation_func.ipp +1 -1
- data/rice/detail/from_ruby.ipp +206 -2
- data/rice/detail/to_ruby.ipp +39 -5
- data/rice/detail/to_ruby_defn.hpp +1 -1
- data/rice/forward_declares.ipp +6 -0
- data/rice/global_function.hpp +0 -4
- data/rice/global_function.ipp +0 -6
- data/rice/rice.hpp +29 -24
- data/rice/stl.hpp +6 -1
- data/sample/callbacks/extconf.rb +0 -1
- data/sample/enum/extconf.rb +0 -1
- data/sample/inheritance/extconf.rb +0 -1
- data/sample/map/extconf.rb +0 -1
- data/test/embed_ruby.cpp +6 -15
- data/test/ext/t1/extconf.rb +0 -1
- data/test/ext/t2/extconf.rb +0 -1
- data/test/extconf.rb +0 -1
- data/test/test_Array.cpp +20 -24
- data/test/test_Attribute.cpp +6 -6
- data/test/test_Class.cpp +8 -47
- data/test/test_Constructor.cpp +0 -2
- data/test/test_Data_Object.cpp +25 -11
- data/test/test_Data_Type.cpp +124 -28
- data/test/test_Director.cpp +12 -13
- data/test/test_Enum.cpp +65 -26
- data/test/test_Inheritance.cpp +9 -9
- data/test/test_Iterator.cpp +134 -5
- data/test/test_Keep_Alive.cpp +7 -7
- data/test/test_Keep_Alive_No_Wrapper.cpp +80 -0
- data/test/test_Memory_Management.cpp +1 -1
- data/test/test_Module.cpp +25 -62
- data/test/test_Object.cpp +75 -3
- data/test/test_Ownership.cpp +12 -13
- data/test/test_Self.cpp +12 -13
- data/test/test_Stl_Map.cpp +696 -0
- data/test/test_Stl_Optional.cpp +3 -3
- data/test/test_Stl_Pair.cpp +38 -2
- data/test/test_Stl_Reference_Wrapper.cpp +102 -0
- data/test/test_Stl_SmartPointer.cpp +49 -9
- data/test/test_Stl_String.cpp +5 -2
- data/test/test_Stl_Unordered_Map.cpp +697 -0
- data/test/test_Stl_Variant.cpp +346 -0
- data/test/test_Stl_Vector.cpp +200 -41
- data/test/test_Struct.cpp +3 -3
- data/test/test_To_From_Ruby.cpp +8 -2
- data/test/test_Tracking.cpp +239 -0
- data/test/unittest.hpp +21 -4
- metadata +24 -13
- data/rice/detail/Exception_Handler.hpp +0 -8
- data/rice/detail/Exception_Handler.ipp +0 -28
- data/rice/detail/Iterator.hpp +0 -23
- data/rice/detail/Iterator.ipp +0 -47
- data/rice/detail/function_traits.hpp +0 -124
- data/rice/detail/method_data.hpp +0 -29
- data/rice/detail/rice_traits.hpp +0 -116
- data/rice/ruby_try_catch.hpp +0 -86
@@ -0,0 +1,346 @@
|
|
1
|
+
#include "unittest.hpp"
|
2
|
+
#include "embed_ruby.hpp"
|
3
|
+
#include <rice/rice.hpp>
|
4
|
+
#include <rice/stl.hpp>
|
5
|
+
|
6
|
+
#include <variant>
|
7
|
+
#include <complex>
|
8
|
+
|
9
|
+
using namespace Rice;
|
10
|
+
|
11
|
+
TESTSUITE(Variant);
|
12
|
+
|
13
|
+
namespace
|
14
|
+
{
|
15
|
+
using Intrinsic_Variant_T = std::variant<
|
16
|
+
std::string,
|
17
|
+
std::complex<double>,
|
18
|
+
std::vector<int>,
|
19
|
+
double,
|
20
|
+
bool,
|
21
|
+
int
|
22
|
+
>;
|
23
|
+
|
24
|
+
inline std::ostream& operator<<(std::ostream& stream, Intrinsic_Variant_T const& variant)
|
25
|
+
{
|
26
|
+
stream << "Variant(" << "index: " << variant.index() << ")";
|
27
|
+
return stream;
|
28
|
+
}
|
29
|
+
|
30
|
+
class MyClass
|
31
|
+
{
|
32
|
+
public:
|
33
|
+
Intrinsic_Variant_T variantString()
|
34
|
+
{
|
35
|
+
// Need to tell compiler this is std::string and not a const char[8]. Because that
|
36
|
+
// becomes const char* which sets the boolean field to true. Oops. https://stackoverflow.com/a/44086312
|
37
|
+
Intrinsic_Variant_T result { std::string("a string") };
|
38
|
+
return result;
|
39
|
+
}
|
40
|
+
|
41
|
+
Intrinsic_Variant_T variantComplex()
|
42
|
+
{
|
43
|
+
using namespace std::complex_literals;
|
44
|
+
Intrinsic_Variant_T result { 1i };
|
45
|
+
return result;
|
46
|
+
}
|
47
|
+
|
48
|
+
Intrinsic_Variant_T variantVector()
|
49
|
+
{
|
50
|
+
Intrinsic_Variant_T result { std::vector<int>{1, 2, 3} };
|
51
|
+
return result;
|
52
|
+
}
|
53
|
+
|
54
|
+
Intrinsic_Variant_T variantDouble()
|
55
|
+
{
|
56
|
+
Intrinsic_Variant_T result { 3.3 };
|
57
|
+
return result;
|
58
|
+
}
|
59
|
+
|
60
|
+
Intrinsic_Variant_T variantBoolTrue()
|
61
|
+
{
|
62
|
+
Intrinsic_Variant_T result { true };
|
63
|
+
return result;
|
64
|
+
}
|
65
|
+
|
66
|
+
Intrinsic_Variant_T variantBoolFalse()
|
67
|
+
{
|
68
|
+
Intrinsic_Variant_T result{ false };
|
69
|
+
return result;
|
70
|
+
}
|
71
|
+
|
72
|
+
Intrinsic_Variant_T variantInt()
|
73
|
+
{
|
74
|
+
Intrinsic_Variant_T result { 5 };
|
75
|
+
return result;
|
76
|
+
}
|
77
|
+
|
78
|
+
Intrinsic_Variant_T variantRoundtrip(Intrinsic_Variant_T variant)
|
79
|
+
{
|
80
|
+
return variant;
|
81
|
+
}
|
82
|
+
|
83
|
+
Intrinsic_Variant_T variantRoundtripReference(Intrinsic_Variant_T variant)
|
84
|
+
{
|
85
|
+
return variant;
|
86
|
+
}
|
87
|
+
|
88
|
+
Intrinsic_Variant_T variant_ = std::string("Initial value");
|
89
|
+
};
|
90
|
+
}
|
91
|
+
|
92
|
+
void makeIntrinsicVariant()
|
93
|
+
{
|
94
|
+
define_class<MyClass>("MyClass").
|
95
|
+
define_constructor(Constructor<MyClass>()).
|
96
|
+
define_method("variant_string", &MyClass::variantString).
|
97
|
+
define_method("variant_complex", &MyClass::variantComplex).
|
98
|
+
define_method("variant_vector", &MyClass::variantVector).
|
99
|
+
define_method("variant_double", &MyClass::variantDouble).
|
100
|
+
define_method("variant_bool_true", &MyClass::variantBoolTrue).
|
101
|
+
define_method("variant_bool_false", &MyClass::variantBoolFalse).
|
102
|
+
define_method("variant_int", &MyClass::variantInt).
|
103
|
+
define_method("roundtrip", &MyClass::variantRoundtrip).
|
104
|
+
define_attr("variant_attr", &MyClass::variant_);
|
105
|
+
}
|
106
|
+
|
107
|
+
TESTCASE(IntrinsicReturns)
|
108
|
+
{
|
109
|
+
using namespace std::complex_literals;
|
110
|
+
|
111
|
+
Module m = define_module("Testing");
|
112
|
+
Object myClass = m.module_eval("MyClass.new");
|
113
|
+
|
114
|
+
Object result = myClass.call("variant_string");
|
115
|
+
ASSERT_EQUAL("a string", detail::From_Ruby<std::string>().convert(result));
|
116
|
+
|
117
|
+
result = myClass.call("variant_complex");
|
118
|
+
ASSERT_EQUAL(1i, detail::From_Ruby<std::complex<double>>().convert(result));
|
119
|
+
|
120
|
+
result = myClass.call("variant_vector");
|
121
|
+
std::vector<int> converted = detail::From_Ruby<std::vector<int>>().convert(result);
|
122
|
+
ASSERT_EQUAL(3, converted.size());
|
123
|
+
|
124
|
+
result = myClass.call("variant_double");
|
125
|
+
ASSERT_EQUAL(3.3, detail::From_Ruby<double>().convert(result));
|
126
|
+
|
127
|
+
result = myClass.call("variant_bool_true");
|
128
|
+
ASSERT(detail::From_Ruby<bool>().convert(result));
|
129
|
+
|
130
|
+
result = myClass.call("variant_bool_false");
|
131
|
+
ASSERT(!detail::From_Ruby<bool>().convert(result));
|
132
|
+
|
133
|
+
result = myClass.call("variant_int");
|
134
|
+
ASSERT_EQUAL(5, detail::From_Ruby<int>().convert(result));
|
135
|
+
}
|
136
|
+
|
137
|
+
TESTCASE(IntrinsicRoundtrip)
|
138
|
+
{
|
139
|
+
using namespace std::complex_literals;
|
140
|
+
|
141
|
+
Module m = define_module("Testing");
|
142
|
+
Object myClass = m.module_eval("MyClass.new");
|
143
|
+
|
144
|
+
std::string code = R"(my_class = MyClass.new
|
145
|
+
my_class.roundtrip("roundtrip string"))";
|
146
|
+
Object result = m.module_eval(code);
|
147
|
+
ASSERT_EQUAL("roundtrip string", detail::From_Ruby<std::string>().convert(result));
|
148
|
+
|
149
|
+
code = R"(my_class = MyClass.new
|
150
|
+
my_class.roundtrip(Complex(2, 3)))";
|
151
|
+
result = m.module_eval(code);
|
152
|
+
ASSERT_EQUAL((2.0 + 3i), detail::From_Ruby<std::complex<double>>().convert(result));
|
153
|
+
|
154
|
+
code = R"(my_class = MyClass.new
|
155
|
+
my_class.roundtrip([1, 2, 3]))";
|
156
|
+
result = m.module_eval(code);
|
157
|
+
std::vector<int> expected = {1, 2, 3};
|
158
|
+
ASSERT_EQUAL(expected, detail::From_Ruby<std::vector<int>>().convert(result));
|
159
|
+
|
160
|
+
code = R"(my_class = MyClass.new
|
161
|
+
my_class.roundtrip(44.4))";
|
162
|
+
result = m.module_eval(code);
|
163
|
+
ASSERT_EQUAL(44.4, detail::From_Ruby<double>().convert(result));
|
164
|
+
|
165
|
+
code = R"(my_class = MyClass.new
|
166
|
+
my_class.roundtrip(true))";
|
167
|
+
result = m.module_eval(code);
|
168
|
+
ASSERT(detail::From_Ruby<bool>().convert(result));
|
169
|
+
|
170
|
+
code = R"(my_class = MyClass.new
|
171
|
+
my_class.roundtrip(false))";
|
172
|
+
result = m.module_eval(code);
|
173
|
+
ASSERT(!detail::From_Ruby<bool>().convert(result));
|
174
|
+
|
175
|
+
code = R"(my_class = MyClass.new
|
176
|
+
my_class.roundtrip(45))";
|
177
|
+
result = m.module_eval(code);
|
178
|
+
ASSERT_EQUAL(45, detail::From_Ruby<int>().convert(result));
|
179
|
+
}
|
180
|
+
|
181
|
+
TESTCASE(VariantAttribute)
|
182
|
+
{
|
183
|
+
Module m = define_module("Testing");
|
184
|
+
Object myClass = m.module_eval("MyClass.new");
|
185
|
+
|
186
|
+
Object result = myClass.call("variant_attr");
|
187
|
+
ASSERT_EQUAL("Initial value", detail::From_Ruby<std::string>().convert(result));
|
188
|
+
|
189
|
+
result = myClass.call("variant_attr=", "Second value");
|
190
|
+
ASSERT_EQUAL("Second value", detail::From_Ruby<std::string>().convert(result));
|
191
|
+
result = myClass.call("variant_attr");
|
192
|
+
ASSERT_EQUAL("Second value", detail::From_Ruby<std::string>().convert(result));
|
193
|
+
|
194
|
+
result = myClass.call("variant_attr=", 77.7);
|
195
|
+
ASSERT_EQUAL(77.7, detail::From_Ruby<double>().convert(result));
|
196
|
+
result = myClass.call("variant_attr");
|
197
|
+
ASSERT_EQUAL(77.7, detail::From_Ruby<double>().convert(result));
|
198
|
+
|
199
|
+
result = myClass.call("variant_attr=", true);
|
200
|
+
ASSERT(detail::From_Ruby<bool>().convert(result));
|
201
|
+
result = myClass.call("variant_attr");
|
202
|
+
ASSERT(detail::From_Ruby<bool>().convert(result));
|
203
|
+
|
204
|
+
result = myClass.call("variant_attr=", false);
|
205
|
+
ASSERT(!detail::From_Ruby<bool>().convert(result));
|
206
|
+
result = myClass.call("variant_attr");
|
207
|
+
ASSERT(!detail::From_Ruby<bool>().convert(result));
|
208
|
+
|
209
|
+
result = myClass.call("variant_attr=", 78);
|
210
|
+
ASSERT_EQUAL(78, detail::From_Ruby<int>().convert(result));
|
211
|
+
result = myClass.call("variant_attr");
|
212
|
+
ASSERT_EQUAL(78, detail::From_Ruby<int>().convert(result));
|
213
|
+
}
|
214
|
+
|
215
|
+
namespace
|
216
|
+
{
|
217
|
+
class MyClass1
|
218
|
+
{
|
219
|
+
public:
|
220
|
+
MyClass1()
|
221
|
+
{
|
222
|
+
int a = 1;
|
223
|
+
}
|
224
|
+
|
225
|
+
std::string sayHello()
|
226
|
+
{
|
227
|
+
return "Hi from MyClass1";
|
228
|
+
}
|
229
|
+
};
|
230
|
+
|
231
|
+
class MyClass2
|
232
|
+
{
|
233
|
+
public:
|
234
|
+
MyClass2()
|
235
|
+
{
|
236
|
+
int a = 2;
|
237
|
+
}
|
238
|
+
|
239
|
+
std::string sayHello()
|
240
|
+
{
|
241
|
+
return "Hi from MyClass2";
|
242
|
+
}
|
243
|
+
};
|
244
|
+
|
245
|
+
using Class_Variant_T = std::variant<std::monostate, MyClass1, MyClass2>;
|
246
|
+
|
247
|
+
Class_Variant_T variantClass(bool myClass1)
|
248
|
+
{
|
249
|
+
if (myClass1)
|
250
|
+
{
|
251
|
+
return MyClass1();
|
252
|
+
}
|
253
|
+
else
|
254
|
+
{
|
255
|
+
return MyClass2();
|
256
|
+
}
|
257
|
+
}
|
258
|
+
|
259
|
+
Class_Variant_T roundTripVariantClass(Class_Variant_T variant)
|
260
|
+
{
|
261
|
+
return variant;
|
262
|
+
}
|
263
|
+
|
264
|
+
Class_Variant_T& roundTripVariantClassRef(Class_Variant_T& variant)
|
265
|
+
{
|
266
|
+
return variant;
|
267
|
+
}
|
268
|
+
}
|
269
|
+
|
270
|
+
void makeClassVariant()
|
271
|
+
{
|
272
|
+
define_class<MyClass1>("MyClass1").
|
273
|
+
define_constructor(Constructor<MyClass1>()).
|
274
|
+
define_method("say_hello", &MyClass1::sayHello);
|
275
|
+
|
276
|
+
define_class<MyClass2>("MyClass2").
|
277
|
+
define_constructor(Constructor<MyClass2>()).
|
278
|
+
define_method("say_hello", &MyClass2::sayHello);
|
279
|
+
|
280
|
+
define_global_function("variant_class", &variantClass);
|
281
|
+
define_global_function("roundtrip_variant_class", &roundTripVariantClass);
|
282
|
+
define_global_function("roundtrip_variant_class_ref", &roundTripVariantClassRef);
|
283
|
+
}
|
284
|
+
|
285
|
+
SETUP(Variant)
|
286
|
+
{
|
287
|
+
embed_ruby();
|
288
|
+
makeIntrinsicVariant();
|
289
|
+
makeClassVariant();
|
290
|
+
}
|
291
|
+
|
292
|
+
TESTCASE(ClassReturns)
|
293
|
+
{
|
294
|
+
Module m = define_module("Testing");
|
295
|
+
|
296
|
+
Data_Object<MyClass1> myclass1 = m.module_eval("variant_class(true)");
|
297
|
+
String hello = myclass1.call("say_hello");
|
298
|
+
ASSERT_EQUAL("Hi from MyClass1", detail::From_Ruby<std::string>().convert(hello));
|
299
|
+
|
300
|
+
Data_Object<MyClass2> myclass2 = m.module_eval("variant_class(false)");
|
301
|
+
hello = myclass2.call("say_hello");
|
302
|
+
ASSERT_EQUAL("Hi from MyClass2", detail::From_Ruby<std::string>().convert(hello));
|
303
|
+
}
|
304
|
+
|
305
|
+
TESTCASE(ClassRoundtrip)
|
306
|
+
{
|
307
|
+
Module m = define_module("Testing");
|
308
|
+
|
309
|
+
Object instance = m.module_eval("MyClass1.new");
|
310
|
+
Object instance2 = m.call("roundtrip_variant_class", instance);
|
311
|
+
String hello = instance2.call("say_hello");
|
312
|
+
ASSERT_EQUAL("Hi from MyClass1", detail::From_Ruby<std::string>().convert(hello));
|
313
|
+
|
314
|
+
instance = m.module_eval("MyClass2.new");
|
315
|
+
instance2 = m.call("roundtrip_variant_class", instance);
|
316
|
+
hello = instance2.call("say_hello");
|
317
|
+
ASSERT_EQUAL("Hi from MyClass2", detail::From_Ruby<std::string>().convert(hello));
|
318
|
+
}
|
319
|
+
|
320
|
+
/* This test case runs successfully on MSVC but not g++. Having stepped through the code with
|
321
|
+
GDB, this sure seems due to a bug with g++. The issue is this variable in created operator():
|
322
|
+
|
323
|
+
Arg_Ts nativeValues = this->getNativeValues(rubyValues, indices);
|
324
|
+
|
325
|
+
And is then passed to invokeNativeFunction as a const Arg_Ts& nativeArgs where Arg_Ts& is
|
326
|
+
std::tuple with one element, a reference to a variant. So it doesn't change and the address
|
327
|
+
of the variable doesn't change. But for some reason g++ resets the
|
328
|
+
the std::variant index to 0 thus breaking the test. Maybe something to do with storing
|
329
|
+
a refernence to a variant in a tuple? */
|
330
|
+
|
331
|
+
#ifdef _MSC_VER
|
332
|
+
TESTCASE(ClassRoundtripRef)
|
333
|
+
{
|
334
|
+
Module m = define_module("Testing");
|
335
|
+
|
336
|
+
Object instance = m.module_eval("MyClass1.new");
|
337
|
+
Object instance2 = m.call("roundtrip_variant_class_ref", instance);
|
338
|
+
String hello = instance2.call("say_hello");
|
339
|
+
ASSERT_EQUAL("Hi from MyClass1", detail::From_Ruby<std::string>().convert(hello));
|
340
|
+
|
341
|
+
instance = m.module_eval("MyClass2.new");
|
342
|
+
instance2 = m.call("roundtrip_variant_class_ref", instance);
|
343
|
+
hello = instance2.call("say_hello");
|
344
|
+
ASSERT_EQUAL("Hi from MyClass2", detail::From_Ruby<std::string>().convert(hello));
|
345
|
+
}
|
346
|
+
#endif
|
data/test/test_Stl_Vector.cpp
CHANGED
@@ -1,5 +1,4 @@
|
|
1
1
|
#include <complex>
|
2
|
-
#include <memory>
|
3
2
|
|
4
3
|
#include "unittest.hpp"
|
5
4
|
#include "embed_ruby.hpp"
|
@@ -31,7 +30,7 @@ namespace
|
|
31
30
|
|
32
31
|
Class makeVectorClass()
|
33
32
|
{
|
34
|
-
Class c= define_class<MyClass>("MyClass").
|
33
|
+
Class c = define_class<MyClass>("MyClass").
|
35
34
|
define_constructor(Constructor<MyClass>()).
|
36
35
|
define_method("stringVector", &MyClass::stringVector);
|
37
36
|
|
@@ -44,15 +43,15 @@ TESTCASE(StringVector)
|
|
44
43
|
|
45
44
|
Class c = define_vector<std::vector<std::string>>("StringVector");
|
46
45
|
|
47
|
-
Object vec = m.
|
46
|
+
Object vec = m.module_eval("$vector = StringVector.new");
|
48
47
|
Object result = vec.call("size");
|
49
48
|
ASSERT_EQUAL(0, detail::From_Ruby<int32_t>().convert(result));
|
50
49
|
|
51
|
-
m.
|
50
|
+
m.module_eval("$vector << 'one' << 'two' << 'two' << 'three'");
|
52
51
|
result = vec.call("size");
|
53
52
|
ASSERT_EQUAL(4, detail::From_Ruby<int32_t>().convert(result));
|
54
53
|
|
55
|
-
m.
|
54
|
+
m.module_eval("$vector.append('four')");
|
56
55
|
result = vec.call("size");
|
57
56
|
ASSERT_EQUAL(5, detail::From_Ruby<int32_t>().convert(result));
|
58
57
|
|
@@ -69,10 +68,10 @@ TESTCASE(WrongType)
|
|
69
68
|
|
70
69
|
Class c = define_vector<std::vector<std::string>>("StringVector");
|
71
70
|
|
72
|
-
Object vec = m.
|
71
|
+
Object vec = m.module_eval("$vector = StringVector.new");
|
73
72
|
ASSERT_EXCEPTION_CHECK(
|
74
73
|
Exception,
|
75
|
-
m.
|
74
|
+
m.module_eval("$vector << 1"),
|
76
75
|
ASSERT_EQUAL("wrong argument type Integer (expected String)", ex.what()));
|
77
76
|
}
|
78
77
|
|
@@ -261,24 +260,6 @@ TESTCASE(Copy)
|
|
261
260
|
ASSERT_NOT_EQUAL(vec.size(), vecCopy.size());
|
262
261
|
}
|
263
262
|
|
264
|
-
TESTCASE(Iterate)
|
265
|
-
{
|
266
|
-
Module m = define_module("Testing");
|
267
|
-
Class c = define_vector<std::vector<double>>("DoubleVector");
|
268
|
-
|
269
|
-
std::string code = R"(vector = DoubleVector.new
|
270
|
-
vector << 5.0 << 6.0 << 7.0
|
271
|
-
updated = vector.map do |value|
|
272
|
-
value * 2.0
|
273
|
-
end)";
|
274
|
-
|
275
|
-
Array result = m.instance_eval(code);
|
276
|
-
ASSERT_EQUAL(3, result.size());
|
277
|
-
ASSERT_EQUAL(10.0, detail::From_Ruby<double>().convert(result[0].value()));
|
278
|
-
ASSERT_EQUAL(12.0, detail::From_Ruby<double>().convert(result[1].value()));
|
279
|
-
ASSERT_EQUAL(14.0, detail::From_Ruby<double>().convert(result[2].value()));
|
280
|
-
}
|
281
|
-
|
282
263
|
namespace
|
283
264
|
{
|
284
265
|
class NotComparable
|
@@ -308,7 +289,7 @@ TESTCASE(NotComparable)
|
|
308
289
|
ASSERT_EQUAL(Qnil, result.value());
|
309
290
|
|
310
291
|
result = vec.call("length");
|
311
|
-
ASSERT_EQUAL(
|
292
|
+
ASSERT_EQUAL(3u, detail::From_Ruby<size_t>().convert(result));
|
312
293
|
|
313
294
|
result = vec.call("include?", NotComparable(2));
|
314
295
|
ASSERT_EQUAL(Qfalse, result.value());
|
@@ -437,13 +418,13 @@ TESTCASE(Printable)
|
|
437
418
|
|
438
419
|
namespace
|
439
420
|
{
|
440
|
-
std::vector<std::complex<
|
421
|
+
std::vector<std::complex<double>> returnComplexVector()
|
441
422
|
{
|
442
|
-
std::complex<
|
443
|
-
std::complex<
|
444
|
-
std::complex<
|
423
|
+
std::complex<double> complex1(1, 1);
|
424
|
+
std::complex<double> complex2(2, 2);
|
425
|
+
std::complex<double> complex3(3, 3);
|
445
426
|
|
446
|
-
std::vector<std::complex<
|
427
|
+
std::vector<std::complex<double>> result;
|
447
428
|
result.push_back(complex1);
|
448
429
|
result.push_back(complex2);
|
449
430
|
result.push_back(complex3);
|
@@ -461,15 +442,27 @@ TESTCASE(AutoRegisterReturn)
|
|
461
442
|
define_global_function("return_complex_vector", &returnComplexVector);
|
462
443
|
|
463
444
|
Module m = define_module("Testing");
|
464
|
-
Object vec = m.
|
465
|
-
ASSERT_EQUAL("Rice::Std::
|
445
|
+
Object vec = m.module_eval("return_complex_vector");
|
446
|
+
ASSERT_EQUAL("Rice::Std::Vector__complex__double___allocator__complex__double______", vec.class_name().str());
|
466
447
|
|
467
448
|
std::string code = R"(vector = return_complex_vector
|
468
449
|
complex = vector.last
|
469
450
|
complex == Complex(3, 3))";
|
470
451
|
|
471
|
-
Object result = m.
|
452
|
+
Object result = m.module_eval(code);
|
472
453
|
ASSERT_EQUAL(Qtrue, result.value());
|
454
|
+
|
455
|
+
// Now register this same vector
|
456
|
+
define_vector<std::vector<std::complex<double>>>("ComplexVector");
|
457
|
+
code = R"(vector = ComplexVector.new)";
|
458
|
+
result = m.module_eval(code);
|
459
|
+
ASSERT(result.is_instance_of(vec.class_of()));
|
460
|
+
|
461
|
+
// Now register it again in the module
|
462
|
+
define_vector_under<std::vector<std::complex<double>>>(m, "ComplexVector2");
|
463
|
+
code = R"(vector = Testing::ComplexVector2.new)";
|
464
|
+
result = m.module_eval(code);
|
465
|
+
ASSERT(result.is_instance_of(vec.class_of()));
|
473
466
|
}
|
474
467
|
|
475
468
|
TESTCASE(AutoRegisterParameter)
|
@@ -482,7 +475,7 @@ TESTCASE(AutoRegisterParameter)
|
|
482
475
|
pass_complex_vector(vector))";
|
483
476
|
|
484
477
|
Module m = define_module("Testing");
|
485
|
-
Object vec = m.
|
478
|
+
Object vec = m.module_eval(code);
|
486
479
|
|
487
480
|
Object result = vec.call("size");
|
488
481
|
ASSERT_EQUAL("Rice::Std::Vector__complex__double___allocator__complex__double______", vec.class_name().str());
|
@@ -507,7 +500,7 @@ TESTCASE(DefaultValue)
|
|
507
500
|
define_global_function("default_vector", &defaultVector, Arg("strings") = std::vector<std::string> { "one", "two", "three" });
|
508
501
|
|
509
502
|
Module m = define_module("Testing");
|
510
|
-
Object result = m.
|
503
|
+
Object result = m.module_eval("default_vector");
|
511
504
|
std::vector<std::string> actual = detail::From_Ruby<std::vector<std::string>>().convert(result);
|
512
505
|
|
513
506
|
std::vector<std::string> expected{ "one", "two", "three" };
|
@@ -518,6 +511,27 @@ TESTCASE(DefaultValue)
|
|
518
511
|
ASSERT_EQUAL(expected[2], actual[2]);
|
519
512
|
}
|
520
513
|
|
514
|
+
TESTCASE(ToArray)
|
515
|
+
{
|
516
|
+
Module m = define_module("Testing");
|
517
|
+
|
518
|
+
Class c = define_vector<std::vector<std::string>>("StringVector").
|
519
|
+
define_constructor(Constructor<std::vector<std::string>>());
|
520
|
+
|
521
|
+
std::string code = R"(vector = StringVector.new
|
522
|
+
vector << "abc"
|
523
|
+
vector << "def"
|
524
|
+
vector << "ghi"
|
525
|
+
vector.to_a)";
|
526
|
+
|
527
|
+
Array array = m.module_eval(code);
|
528
|
+
ASSERT_EQUAL(3u, array.size());
|
529
|
+
|
530
|
+
ASSERT_EQUAL("abc", detail::From_Ruby<std::string>().convert(array[0].value()));
|
531
|
+
ASSERT_EQUAL("def", detail::From_Ruby<std::string>().convert(array[1].value()));
|
532
|
+
ASSERT_EQUAL("ghi", detail::From_Ruby<std::string>().convert(array[2].value()));
|
533
|
+
}
|
534
|
+
|
521
535
|
namespace
|
522
536
|
{
|
523
537
|
std::vector<int> ints;
|
@@ -553,7 +567,7 @@ TESTCASE(ArrayToVector)
|
|
553
567
|
Module m = define_module("Testing");
|
554
568
|
|
555
569
|
std::string code = "array_to_vector([7, 9, 1_000_000], [49.0, 78.0, 999.0], %w[one two three])";
|
556
|
-
m.
|
570
|
+
m.module_eval(code);
|
557
571
|
|
558
572
|
ASSERT_EQUAL(3, ints.size());
|
559
573
|
ASSERT_EQUAL(7, ints[0]);
|
@@ -578,7 +592,7 @@ TESTCASE(ArrayToVectorRefs)
|
|
578
592
|
Module m = define_module("Testing");
|
579
593
|
|
580
594
|
std::string code = "array_to_vector_refs([8, 10, 1_000_001], [50.0, 79.0, 1_000.0], %w[eleven twelve thirteen])";
|
581
|
-
m.
|
595
|
+
m.module_eval(code);
|
582
596
|
|
583
597
|
ASSERT_EQUAL(3, ints.size());
|
584
598
|
ASSERT_EQUAL(8, ints[0]);
|
@@ -603,7 +617,7 @@ TESTCASE(ArrayToVectorPointers)
|
|
603
617
|
Module m = define_module("Testing");
|
604
618
|
|
605
619
|
std::string code = "array_to_vector_pointers([9, 11, 1_000_002], [51.0, 80.0, 1_001.0], %w[fourteen fifteen sixteen])";
|
606
|
-
m.
|
620
|
+
m.module_eval(code);
|
607
621
|
|
608
622
|
ASSERT_EQUAL(3, ints.size());
|
609
623
|
ASSERT_EQUAL(9, ints[0]);
|
@@ -631,7 +645,7 @@ TESTCASE(ArrayToVectorWrongTypes)
|
|
631
645
|
|
632
646
|
ASSERT_EXCEPTION_CHECK(
|
633
647
|
Exception,
|
634
|
-
m.
|
648
|
+
m.module_eval(code),
|
635
649
|
ASSERT_EQUAL("wrong argument type Float (expected String)", ex.what())
|
636
650
|
);
|
637
651
|
}
|
@@ -646,7 +660,152 @@ TESTCASE(ArrayToVectorMixedTypes)
|
|
646
660
|
|
647
661
|
ASSERT_EXCEPTION_CHECK(
|
648
662
|
Exception,
|
649
|
-
m.
|
663
|
+
m.module_eval(code),
|
650
664
|
ASSERT_EQUAL("no implicit conversion of String into Integer", ex.what())
|
651
665
|
);
|
652
666
|
}
|
667
|
+
|
668
|
+
namespace
|
669
|
+
{
|
670
|
+
class Factory
|
671
|
+
{
|
672
|
+
public:
|
673
|
+
std::vector<std::string>* returnPointer()
|
674
|
+
{
|
675
|
+
return &this->instance_;
|
676
|
+
}
|
677
|
+
|
678
|
+
std::vector<std::string>& returnReference()
|
679
|
+
{
|
680
|
+
return this->instance_;
|
681
|
+
}
|
682
|
+
|
683
|
+
std::vector<std::string> returnValue()
|
684
|
+
{
|
685
|
+
return this->instance_;
|
686
|
+
}
|
687
|
+
|
688
|
+
public:
|
689
|
+
static inline std::vector<std::string> instance_{ "one", "two", "three" };
|
690
|
+
};
|
691
|
+
|
692
|
+
std::ostream& operator<<(std::ostream& stream, const std::vector<std::string>& vector)
|
693
|
+
{
|
694
|
+
stream << "Vector";
|
695
|
+
return stream;
|
696
|
+
}
|
697
|
+
}
|
698
|
+
|
699
|
+
void createFactoryClass()
|
700
|
+
{
|
701
|
+
define_class<Factory>("Factory").
|
702
|
+
define_constructor(Constructor<Factory>()).
|
703
|
+
define_method("pointer", &Factory::returnPointer).
|
704
|
+
define_method("reference", &Factory::returnReference).
|
705
|
+
define_method("value", &Factory::returnValue);
|
706
|
+
}
|
707
|
+
|
708
|
+
TESTCASE(Returns)
|
709
|
+
{
|
710
|
+
createFactoryClass();
|
711
|
+
Module m = define_module("TestingModule");
|
712
|
+
Object factory = m.module_eval("Factory.new");
|
713
|
+
|
714
|
+
std::vector<std::string> expected{ "one", "two", "three" };
|
715
|
+
|
716
|
+
Data_Object<std::vector<std::string>> vec1 = factory.call("pointer");
|
717
|
+
ASSERT_EQUAL(expected, *vec1);
|
718
|
+
|
719
|
+
Data_Object<std::vector<std::string>> vec2 = factory.call("reference");
|
720
|
+
ASSERT_EQUAL(expected, *vec2);
|
721
|
+
|
722
|
+
Data_Object<std::vector<std::string>> vec3 = factory.call("value");
|
723
|
+
ASSERT_EQUAL(expected, *vec3);
|
724
|
+
}
|
725
|
+
|
726
|
+
TESTCASE(Iterate)
|
727
|
+
{
|
728
|
+
Module m = define_module("Testing");
|
729
|
+
Class c = define_vector<std::vector<double>>("DoubleVector");
|
730
|
+
|
731
|
+
std::string code = R"(vector = DoubleVector.new
|
732
|
+
vector << 5.0 << 6.0 << 7.0
|
733
|
+
updated = vector.map do |value|
|
734
|
+
value * 2.0
|
735
|
+
end)";
|
736
|
+
|
737
|
+
Array result = m.module_eval(code);
|
738
|
+
ASSERT_EQUAL(3, result.size());
|
739
|
+
ASSERT_EQUAL(10.0, detail::From_Ruby<double>().convert(result[0].value()));
|
740
|
+
ASSERT_EQUAL(12.0, detail::From_Ruby<double>().convert(result[1].value()));
|
741
|
+
ASSERT_EQUAL(14.0, detail::From_Ruby<double>().convert(result[2].value()));
|
742
|
+
}
|
743
|
+
|
744
|
+
TESTCASE(ToEnumPointer)
|
745
|
+
{
|
746
|
+
createFactoryClass();
|
747
|
+
Module m = define_module("TestingModule");
|
748
|
+
|
749
|
+
std::string code = R"(factory = Factory.new
|
750
|
+
vector = factory.pointer
|
751
|
+
updated = vector.each.map do |value|
|
752
|
+
value + "_updated"
|
753
|
+
end)";
|
754
|
+
|
755
|
+
Array result = m.module_eval(code);
|
756
|
+
|
757
|
+
ASSERT_EQUAL(3, result.size());
|
758
|
+
ASSERT_EQUAL("one_updated", detail::From_Ruby<std::string>().convert(result[0].value()));
|
759
|
+
ASSERT_EQUAL("two_updated", detail::From_Ruby<std::string>().convert(result[1].value()));
|
760
|
+
ASSERT_EQUAL("three_updated", detail::From_Ruby<std::string>().convert(result[2].value()));
|
761
|
+
}
|
762
|
+
|
763
|
+
TESTCASE(ToEnumReference)
|
764
|
+
{
|
765
|
+
createFactoryClass();
|
766
|
+
Module m = define_module("TestingModule");
|
767
|
+
|
768
|
+
std::string code = R"(factory = Factory.new
|
769
|
+
vector = factory.reference
|
770
|
+
updated = vector.each.map do |value|
|
771
|
+
value + "_updated"
|
772
|
+
end)";
|
773
|
+
|
774
|
+
Array result = m.module_eval(code);
|
775
|
+
|
776
|
+
ASSERT_EQUAL(3, result.size());
|
777
|
+
ASSERT_EQUAL("one_updated", detail::From_Ruby<std::string>().convert(result[0].value()));
|
778
|
+
ASSERT_EQUAL("two_updated", detail::From_Ruby<std::string>().convert(result[1].value()));
|
779
|
+
ASSERT_EQUAL("three_updated", detail::From_Ruby<std::string>().convert(result[2].value()));
|
780
|
+
}
|
781
|
+
|
782
|
+
TESTCASE(ToEnumValue)
|
783
|
+
{
|
784
|
+
createFactoryClass();
|
785
|
+
Module m = define_module("TestingModule");
|
786
|
+
|
787
|
+
std::string code = R"(factory = Factory.new
|
788
|
+
vector = factory.value
|
789
|
+
updated = vector.each.map do |value|
|
790
|
+
value + "_updated"
|
791
|
+
end)";
|
792
|
+
|
793
|
+
Array result = m.module_eval(code);
|
794
|
+
|
795
|
+
ASSERT_EQUAL(3, result.size());
|
796
|
+
ASSERT_EQUAL("one_updated", detail::From_Ruby<std::string>().convert(result[0].value()));
|
797
|
+
ASSERT_EQUAL("two_updated", detail::From_Ruby<std::string>().convert(result[1].value()));
|
798
|
+
ASSERT_EQUAL("three_updated", detail::From_Ruby<std::string>().convert(result[2].value()));
|
799
|
+
}
|
800
|
+
|
801
|
+
TESTCASE(ToEnumSize)
|
802
|
+
{
|
803
|
+
createFactoryClass();
|
804
|
+
Module m = define_module("TestingModule");
|
805
|
+
Object factory = m.module_eval("Factory.new");
|
806
|
+
Object vector = factory.call("pointer");
|
807
|
+
Object enumerable = vector.call("each");
|
808
|
+
Object result = enumerable.call("size");
|
809
|
+
|
810
|
+
ASSERT_EQUAL(3, detail::From_Ruby<int>().convert(result));
|
811
|
+
}
|