symengine 0.0.1 → 0.0.2

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.
Files changed (49) hide show
  1. checksums.yaml +4 -4
  2. data/CMakeLists.txt +17 -0
  3. data/Gemfile +4 -0
  4. data/LICENSE +1 -76
  5. data/README.md +29 -11
  6. data/cmake/FindRuby.cmake +286 -0
  7. data/ext/symengine/CMakeLists.txt +26 -0
  8. data/ext/symengine/extconf.rb +15 -0
  9. data/ext/symengine/ruby_basic.c +254 -0
  10. data/ext/symengine/ruby_basic.h +53 -0
  11. data/ext/symengine/ruby_integer.c +8 -0
  12. data/ext/symengine/ruby_integer.h +8 -0
  13. data/ext/symengine/ruby_rational.c +23 -0
  14. data/ext/symengine/ruby_rational.h +8 -0
  15. data/ext/symengine/ruby_symbol.c +13 -0
  16. data/ext/symengine/ruby_symbol.h +8 -0
  17. data/ext/symengine/symengine.c +49 -0
  18. data/ext/symengine/symengine.h +15 -0
  19. data/ext/symengine/symengine_macros.c +49 -0
  20. data/ext/symengine/symengine_macros.h +21 -0
  21. data/spec/arit_spec.rb +146 -0
  22. data/spec/basic_spec.rb +217 -0
  23. data/spec/integer_spec.rb +56 -0
  24. data/spec/rational_spec.rb +51 -0
  25. data/spec/spec_helper.rb +96 -0
  26. data/spec/symbol_spec.rb +20 -0
  27. data/symengine.gemspec +19 -0
  28. metadata +29 -26
  29. data/lib/symengine/CMakeFiles/CMakeDirectoryInformation.cmake +0 -16
  30. data/lib/symengine/CMakeFiles/progress.marks +0 -1
  31. data/lib/symengine/CMakeFiles/symengine_ruby.dir/C.includecache +0 -138
  32. data/lib/symengine/CMakeFiles/symengine_ruby.dir/DependInfo.cmake +0 -33
  33. data/lib/symengine/CMakeFiles/symengine_ruby.dir/__/__/ext/symengine/ruby_basic.c.o +0 -0
  34. data/lib/symengine/CMakeFiles/symengine_ruby.dir/__/__/ext/symengine/ruby_integer.c.o +0 -0
  35. data/lib/symengine/CMakeFiles/symengine_ruby.dir/__/__/ext/symengine/ruby_rational.c.o +0 -0
  36. data/lib/symengine/CMakeFiles/symengine_ruby.dir/__/__/ext/symengine/ruby_symbol.c.o +0 -0
  37. data/lib/symengine/CMakeFiles/symengine_ruby.dir/__/__/ext/symengine/symengine.c.o +0 -0
  38. data/lib/symengine/CMakeFiles/symengine_ruby.dir/__/__/ext/symengine/symengine_macros.c.o +0 -0
  39. data/lib/symengine/CMakeFiles/symengine_ruby.dir/build.make +0 -241
  40. data/lib/symengine/CMakeFiles/symengine_ruby.dir/cmake_clean.cmake +0 -15
  41. data/lib/symengine/CMakeFiles/symengine_ruby.dir/depend.internal +0 -94
  42. data/lib/symengine/CMakeFiles/symengine_ruby.dir/depend.make +0 -94
  43. data/lib/symengine/CMakeFiles/symengine_ruby.dir/flags.make +0 -8
  44. data/lib/symengine/CMakeFiles/symengine_ruby.dir/link.txt +0 -1
  45. data/lib/symengine/CMakeFiles/symengine_ruby.dir/progress.make +0 -7
  46. data/lib/symengine/CTestTestfile.cmake +0 -6
  47. data/lib/symengine/Makefile +0 -347
  48. data/lib/symengine/cmake_install.cmake +0 -34
  49. data/lib/symengine/symengine.so +0 -0
@@ -0,0 +1,26 @@
1
+ set(RUBY_WRAPPER_SRC
2
+ ruby_basic.c
3
+ ruby_symbol.c
4
+ ruby_integer.c
5
+ ruby_rational.c
6
+ symengine_macros.c
7
+ symengine.c
8
+ )
9
+
10
+ include_directories(BEFORE ${RUBY_INCLUDE_DIRS})
11
+
12
+ add_library(symengine_ruby SHARED ${RUBY_WRAPPER_SRC})
13
+ target_link_libraries(symengine_ruby ${SYMENGINE_LIBRARIES} ${RUBY_LIBRARY})
14
+ set_target_properties(symengine_ruby PROPERTIES
15
+ PREFIX ""
16
+ SUFFIX ".so"
17
+ OUTPUT_NAME "symengine"
18
+ LIBRARY_OUTPUT_DIRECTORY "${ruby_wrapper_BINARY_DIR}/lib/symengine"
19
+ )
20
+
21
+ # Ruby gems require a install target.
22
+ install(TARGETS symengine_ruby
23
+ RUNTIME DESTINATION lib/symengine
24
+ ARCHIVE DESTINATION lib/symengine
25
+ LIBRARY DESTINATION lib/symengine
26
+ )
@@ -0,0 +1,15 @@
1
+ require 'rbconfig'
2
+
3
+ ruby_executable = File.join(RbConfig::CONFIG['bindir'], RbConfig::CONFIG['RUBY_INSTALL_NAME'] + RbConfig::CONFIG['EXEEXT'])
4
+
5
+ generator = ""
6
+
7
+ if (RbConfig::CONFIG['host_os'] =~ /mingw/)
8
+ generator = '-G "MSYS Makefiles"'
9
+ elsif (RbConfig::CONFIG['host_os'] =~ /cygwin/)
10
+ generator = '-G "Unix Makefiles"'
11
+ elsif (RbConfig::CONFIG['host_os'] =~ /mswin/)
12
+ generator = '-G "NMake Makefiles"'
13
+ end
14
+
15
+ exec 'cmake %s -DCMAKE_INSTALL_PREFIX=../../ -DRUBY_EXECUTABLE=%s %s ../../ ' % [generator, ruby_executable, ARGV.join(" ")]
@@ -0,0 +1,254 @@
1
+ #include "ruby_basic.h"
2
+
3
+ void cbasic_free(void *ptr){
4
+ basic_struct *basic_ptr = ptr;
5
+ basic_free_stack(basic_ptr);
6
+ }
7
+
8
+ void cbasic_free_heap(void *ptr) {
9
+ basic_struct *basic_ptr = ptr;
10
+ basic_free_heap(basic_ptr);
11
+ }
12
+
13
+ VALUE cbasic_alloc(VALUE klass){
14
+ basic_struct *struct_ptr = basic_new_heap();
15
+ return Data_Wrap_Struct(klass, NULL, cbasic_free_heap, struct_ptr);
16
+ }
17
+
18
+ VALUE cbasic_binary_op(VALUE self, VALUE operand2, void (*cwfunc_ptr)(basic_struct*, const basic_struct*, const basic_struct*)){
19
+ basic_struct *this, *cresult;
20
+ VALUE result;
21
+
22
+ basic cbasic_operand2;
23
+ basic_new_stack(cbasic_operand2);
24
+
25
+ Data_Get_Struct(self, basic_struct, this);
26
+ sympify(operand2, cbasic_operand2);
27
+
28
+ cresult = basic_new_heap();
29
+ cwfunc_ptr(cresult, this, cbasic_operand2);
30
+ result = Data_Wrap_Struct(Klass_of_Basic(cresult), NULL , cbasic_free_heap, cresult);
31
+ basic_free_stack(cbasic_operand2);
32
+
33
+ return result;
34
+ }
35
+
36
+ VALUE cbasic_unary_op(VALUE self, void (*cwfunc_ptr)(basic_struct*, const basic_struct*)){
37
+ basic_struct *this, *cresult;
38
+ VALUE result;
39
+
40
+ Data_Get_Struct(self, basic_struct, this);
41
+
42
+ cresult = basic_new_heap();
43
+ cwfunc_ptr(cresult, this);
44
+ result = Data_Wrap_Struct(Klass_of_Basic(cresult), NULL , cbasic_free_heap, cresult);
45
+
46
+ return result;
47
+ }
48
+
49
+ VALUE cbasic_add(VALUE self, VALUE operand2){
50
+ return cbasic_binary_op(self, operand2, basic_add);
51
+ }
52
+
53
+ VALUE cbasic_sub(VALUE self, VALUE operand2){
54
+ return cbasic_binary_op(self, operand2, basic_sub);
55
+ }
56
+
57
+ VALUE cbasic_mul(VALUE self, VALUE operand2){
58
+ return cbasic_binary_op(self, operand2, basic_mul);
59
+ }
60
+
61
+ VALUE cbasic_div(VALUE self, VALUE operand2){
62
+ return cbasic_binary_op(self, operand2, basic_div);
63
+ }
64
+
65
+ VALUE cbasic_pow(VALUE self, VALUE operand2){
66
+ return cbasic_binary_op(self, operand2, basic_pow);
67
+ }
68
+
69
+ VALUE cbasic_diff(VALUE self, VALUE operand2) {
70
+ basic_struct *this, *cresult;
71
+ VALUE result;
72
+
73
+ basic cbasic_operand2;
74
+ basic_new_stack(cbasic_operand2);
75
+
76
+ Data_Get_Struct(self, basic_struct, this);
77
+ sympify(operand2, cbasic_operand2);
78
+
79
+ cresult = basic_new_heap();
80
+ int status = basic_diff(cresult, this, cbasic_operand2);
81
+ if (status == 0) {
82
+ basic_free_stack(cbasic_operand2);
83
+ basic_free_heap(cresult);
84
+ return Qnil;
85
+ }
86
+ result = Data_Wrap_Struct(Klass_of_Basic(cresult), NULL , cbasic_free_heap, cresult);
87
+ basic_free_stack(cbasic_operand2);
88
+
89
+ return result;
90
+ }
91
+
92
+ VALUE cbasic_eq(VALUE self, VALUE operand2) {
93
+ basic_struct *this;
94
+
95
+ basic cbasic_operand2;
96
+ basic_new_stack(cbasic_operand2);
97
+ Data_Get_Struct(self, basic_struct, this);
98
+ sympify(operand2, cbasic_operand2);
99
+
100
+ VALUE ret_val = basic_eq(this, cbasic_operand2) ? Qtrue : Qfalse;
101
+ basic_free_stack(cbasic_operand2);
102
+
103
+ return ret_val;
104
+ }
105
+
106
+ VALUE cbasic_neq(VALUE self, VALUE operand2) {
107
+ basic_struct *this;
108
+
109
+ basic cbasic_operand2;
110
+ basic_new_stack(cbasic_operand2);
111
+ Data_Get_Struct(self, basic_struct, this);
112
+ sympify(operand2, cbasic_operand2);
113
+
114
+ VALUE ret_val = basic_neq(this, cbasic_operand2) ? Qtrue : Qfalse;
115
+ basic_free_stack(cbasic_operand2);
116
+
117
+ return ret_val;
118
+ }
119
+
120
+ VALUE cbasic_neg(VALUE self){
121
+ return cbasic_unary_op(self, basic_neg);
122
+ }
123
+
124
+ VALUE cbasic_get_args(VALUE self) {
125
+ basic_struct *this, *iterator_basic;
126
+ CVecBasic *args = vecbasic_new();
127
+ int size = 0;
128
+
129
+ Data_Get_Struct(self, basic_struct, this);
130
+ basic_get_args(this, args);
131
+
132
+ size = vecbasic_size(args);
133
+ VALUE ruby_array = rb_ary_new2(size);
134
+ int i = 0;
135
+ VALUE temp = NULL;
136
+ for(i = 0; i < size; i++) {
137
+ basic_struct *temp_basic = basic_new_heap();
138
+ vecbasic_get(args, i, temp_basic);
139
+ temp = Data_Wrap_Struct(rb_obj_class(self), NULL , cbasic_free_heap, temp_basic);
140
+ rb_ary_push(ruby_array, temp);
141
+ }
142
+ vecbasic_free(args);
143
+ return ruby_array;
144
+ }
145
+
146
+ VALUE cbasic_free_symbols(VALUE self) {
147
+ basic_struct *this, *iterator_basic;
148
+ CSetBasic *symbols = setbasic_new();
149
+ int size = 0;
150
+
151
+ Data_Get_Struct(self, basic_struct, this);
152
+ basic_free_symbols(this, symbols);
153
+
154
+ size = setbasic_size(symbols);
155
+ VALUE ruby_array = rb_ary_new2(size);
156
+ int i = 0;
157
+ VALUE temp = NULL;
158
+ for(i = 0; i < size; i++) {
159
+ basic_struct *temp_basic = basic_new_heap();
160
+ setbasic_get(symbols, i, temp_basic);
161
+ temp = Data_Wrap_Struct(rb_obj_class(self), NULL , cbasic_free_heap, temp_basic);
162
+ rb_ary_push(ruby_array, temp);
163
+ }
164
+ setbasic_free(symbols);
165
+ return ruby_array;
166
+ }
167
+
168
+ VALUE cbasic_to_str(VALUE self){
169
+ basic_struct *this;
170
+ char *str_ptr;
171
+ VALUE result;
172
+
173
+ Data_Get_Struct(self, basic_struct, this);
174
+
175
+ str_ptr = basic_str(this);
176
+ result = rb_str_new_cstr(str_ptr);
177
+ basic_str_free(str_ptr);
178
+
179
+ return result;
180
+ }
181
+
182
+ VALUE cbasic_expand(VALUE self){
183
+ return cbasic_unary_op(self, basic_expand);
184
+ }
185
+
186
+ VALUE cbasic_hash(VALUE self){
187
+ basic_struct *this;
188
+ Data_Get_Struct(self, basic_struct, this);
189
+ // All ruby objects return FIXNUM when `hash` method is called.
190
+ // Though this function returns BIGNUM it won't be a problem, since
191
+ // we need proper comparison only among objects in SymEngine.
192
+ // The objects that should have the same hash will always match
193
+ // and when comparing to the FIXNUM from hash of other ruby objects,
194
+ // it will return false as it is supposed to.
195
+ // However, an alternate implementation is given below
196
+ // long lhash = basic_hash(this) % FIX2LONG(FIXNUM_MAX);
197
+ // return LONG2FIX(lhash);
198
+ return SIZET2NUM(basic_hash(this));
199
+ }
200
+
201
+ int insert_entries(VALUE key, VALUE val, VALUE input) {
202
+ CMapBasicBasic *cmapbb;
203
+ Data_Get_Struct(input, CMapBasicBasic, cmapbb);
204
+
205
+ basic ckey, cval;
206
+ basic_new_stack(ckey);
207
+ basic_new_stack(cval);
208
+ sympify(key, ckey);
209
+ sympify(val, cval);
210
+
211
+ mapbasicbasic_insert(cmapbb, ckey, cval);
212
+
213
+ basic_free_stack(ckey);
214
+ basic_free_stack(cval);
215
+ }
216
+
217
+ VALUE cbasic_subs(int argc, VALUE *argv, VALUE self) {
218
+ basic_struct *this, *cresult;
219
+ cresult = basic_new_heap();
220
+
221
+ VALUE val_a, val_b;
222
+ Data_Get_Struct(self, basic_struct, this);
223
+
224
+ rb_scan_args(argc, argv, "11", &val_a, &val_b); // 1 mandatory and 1 optional parameter
225
+ if (argc == 1) {
226
+ Check_Type(val_a, T_HASH);
227
+ CMapBasicBasic *cmapbb = mapbasicbasic_new();
228
+ VALUE mapbb = Data_Wrap_Struct(rb_cObject, NULL, mapbasicbasic_free, cmapbb);
229
+
230
+ rb_hash_foreach(val_a, insert_entries, mapbb);
231
+ basic_subs(cresult, this, cmapbb);
232
+ } else {
233
+ basic a, b;
234
+ basic_new_stack(a);
235
+ basic_new_stack(b);
236
+
237
+ sympify(val_a, a);
238
+ sympify(val_b, b);
239
+ basic_subs2(cresult, this, a, b);
240
+
241
+ basic_free_stack(a);
242
+ basic_free_stack(b);
243
+ }
244
+
245
+ return Data_Wrap_Struct(Klass_of_Basic(cresult), NULL, cbasic_free_heap, cresult);
246
+ }
247
+
248
+ VALUE cbasic_coerce(VALUE self, VALUE other){
249
+ basic_struct *cbasic_operand2;
250
+ cbasic_operand2 = basic_new_heap();
251
+ sympify(other, cbasic_operand2);
252
+ VALUE new_other = Data_Wrap_Struct(Klass_of_Basic(cbasic_operand2), NULL , cbasic_free_heap, cbasic_operand2);
253
+ return rb_assoc_new(new_other, self);
254
+ }
@@ -0,0 +1,53 @@
1
+ #ifndef RUBY_BASIC_H_
2
+ #define RUBY_BASIC_H_
3
+
4
+ #include <ruby.h>
5
+ #include <symengine/cwrapper.h>
6
+
7
+ #include "symengine_macros.h"
8
+
9
+ void cbasic_free(void *ptr);
10
+
11
+ void cbasic_free_heap(void *ptr);
12
+
13
+ VALUE cbasic_alloc(VALUE klass);
14
+
15
+ VALUE cbasic_binary_op(VALUE self, VALUE operand2, void (*cwfunc_ptr)(basic_struct*, const basic_struct*, const basic_struct*));
16
+
17
+ VALUE cbasic_unary_op(VALUE self, void (*cwfunc_ptr)(basic_struct*, const basic_struct*));
18
+
19
+ VALUE cbasic_add(VALUE self, VALUE operand2);
20
+
21
+ VALUE cbasic_sub(VALUE self, VALUE operand2);
22
+
23
+ VALUE cbasic_mul(VALUE self, VALUE operand2);
24
+
25
+ VALUE cbasic_div(VALUE self, VALUE operand2);
26
+
27
+ VALUE cbasic_pow(VALUE self, VALUE operand2);
28
+
29
+ VALUE cbasic_diff(VALUE self, VALUE operand2);
30
+
31
+ VALUE cbasic_eq(VALUE self, VALUE operand2);
32
+
33
+ VALUE cbasic_neq(VALUE self, VALUE operand2);
34
+
35
+ VALUE cbasic_neg(VALUE self);
36
+
37
+ VALUE cbasic_get_args(VALUE self);
38
+
39
+ VALUE cbasic_free_symbols(VALUE self);
40
+
41
+ VALUE cbasic_to_str(VALUE self);
42
+
43
+ VALUE cbasic_expand(VALUE self);
44
+
45
+ VALUE cbasic_hash(VALUE self);
46
+
47
+ int insert_entries(VALUE key, VALUE val, VALUE val_map_basic_basic);
48
+
49
+ VALUE cbasic_subs(int argc, VALUE *argv, VALUE self);
50
+
51
+ VALUE cbasic_coerce(VALUE self, VALUE other);
52
+
53
+ #endif //RUBY_BASIC_H_
@@ -0,0 +1,8 @@
1
+ #include "ruby_integer.h"
2
+
3
+ VALUE cinteger_init(VALUE self, VALUE num_value) {
4
+ basic_struct *this;
5
+ Data_Get_Struct(self, basic_struct, this);
6
+ GET_SYMINTFROMVAL(num_value, this);
7
+ return self;
8
+ }
@@ -0,0 +1,8 @@
1
+ #ifndef RUBY_INTEGER_H_
2
+ #define RUBY_INTEGER_H_
3
+
4
+ #include "ruby_basic.h"
5
+
6
+ VALUE cinteger_init(VALUE self, VALUE num_value);
7
+
8
+ #endif //RUBY_INTEGER_H_
@@ -0,0 +1,23 @@
1
+ #include "ruby_rational.h"
2
+
3
+ VALUE crational_init(VALUE self, VALUE rat_value) {
4
+ basic_struct *this;
5
+ basic num_basic, den_basic;
6
+
7
+ basic_new_stack(num_basic);
8
+ basic_new_stack(den_basic);
9
+
10
+ Data_Get_Struct(self, basic_struct, this);
11
+
12
+ VALUE num, den;
13
+ num = rb_funcall(rat_value, rb_intern("numerator"), 0, NULL);
14
+ den = rb_funcall(rat_value, rb_intern("denominator"), 0, NULL);
15
+
16
+ GET_SYMINTFROMVAL(num, num_basic);
17
+ GET_SYMINTFROMVAL(den, den_basic);
18
+
19
+ rational_set(this, num_basic, den_basic);
20
+ basic_free_stack(num_basic);
21
+ basic_free_stack(den_basic);
22
+ return self;
23
+ }
@@ -0,0 +1,8 @@
1
+ #ifndef RUBY_RATIONAL_H_
2
+ #define RUBY_RATIONAL_H_
3
+
4
+ #include "ruby_basic.h"
5
+
6
+ VALUE crational_init(VALUE self, VALUE rat_value);
7
+
8
+ #endif //RUBY_RATIONAL_H_
@@ -0,0 +1,13 @@
1
+ #include "ruby_symbol.h"
2
+
3
+ VALUE csymbol_init(VALUE self, VALUE name) {
4
+ Check_Type(name, T_STRING);
5
+ basic_struct *this;
6
+ char *str_ptr = StringValueCStr(name);
7
+
8
+ Data_Get_Struct(self, basic_struct, this);
9
+
10
+ symbol_set(this, str_ptr);
11
+
12
+ return self;
13
+ }
@@ -0,0 +1,8 @@
1
+ #ifndef RUBY_SYMBOL_H_
2
+ #define RUBY_SYMBOL_H_
3
+
4
+ #include "ruby_basic.h"
5
+
6
+ VALUE csymbol_init(VALUE self, VALUE name);
7
+
8
+ #endif //RUBY_SYMBOL_H_
@@ -0,0 +1,49 @@
1
+ #include "ruby_basic.h"
2
+ #include "ruby_symbol.h"
3
+ #include "ruby_integer.h"
4
+ #include "ruby_rational.h"
5
+ #include "symengine.h"
6
+
7
+ ///////////////////
8
+ // Ruby Bindings //
9
+ ///////////////////
10
+
11
+ void Init_symengine() {
12
+ m_symengine = rb_define_module("SymEngine");
13
+
14
+ //Basic class
15
+ c_basic = rb_define_class_under(m_symengine, "Basic", rb_cObject);
16
+ rb_define_alloc_func(c_basic, cbasic_alloc);
17
+ rb_define_method(c_basic, "+", cbasic_add, 1);
18
+ rb_define_method(c_basic, "-", cbasic_sub, 1);
19
+ rb_define_method(c_basic, "*", cbasic_mul, 1);
20
+ rb_define_method(c_basic, "/", cbasic_div, 1);
21
+ rb_define_method(c_basic, "**", cbasic_pow, 1);
22
+ rb_define_method(c_basic, "diff", cbasic_diff, 1);
23
+ rb_define_method(c_basic, "==", cbasic_eq, 1);
24
+ rb_define_method(c_basic, "eql?", cbasic_eq, 1);
25
+ rb_define_method(c_basic, "!=", cbasic_neq, 1);
26
+ rb_define_method(c_basic, "-@", cbasic_neg, 0);
27
+ rb_define_method(c_basic, "to_s", cbasic_to_str, 0);
28
+ rb_define_method(c_basic, "expand", cbasic_expand, 0);
29
+ rb_define_method(c_basic, "args", cbasic_get_args, 0);
30
+ rb_define_protected_method(c_basic, "pr_free_symbols", cbasic_free_symbols, 0);
31
+ rb_define_method(c_basic, "hash", cbasic_hash, 0);
32
+ rb_define_method(c_basic, "subs", cbasic_subs, -1);
33
+ rb_define_method(c_basic, "coerce", cbasic_coerce, 1);
34
+
35
+ //Symbol class
36
+ c_symbol = rb_define_class_under(m_symengine, "Symbol", c_basic);
37
+ rb_define_alloc_func(c_symbol, cbasic_alloc);
38
+ rb_define_method(c_symbol, "initialize", csymbol_init, 1);
39
+
40
+ //Integer class
41
+ c_integer = rb_define_class_under(m_symengine, "Integer", c_basic);
42
+ rb_define_alloc_func(c_integer, cbasic_alloc);
43
+ rb_define_method(c_integer, "initialize", cinteger_init, 1);
44
+
45
+ //Rational class
46
+ c_rational = rb_define_class_under(m_symengine, "Rational", c_basic);
47
+ rb_define_alloc_func(c_rational, cbasic_alloc);
48
+ rb_define_method(c_rational, "initialize", crational_init, 1);
49
+ }