quadmath 0.1.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 +7 -0
- data/CHANGELOG.md +11 -0
- data/CODE_OF_CONDUCT.md +132 -0
- data/LICENSE.txt +21 -0
- data/README.md +160 -0
- data/Rakefile +14 -0
- data/ext/quadmath/complex128.c +494 -0
- data/ext/quadmath/extconf.rb +15 -0
- data/ext/quadmath/float128.c +638 -0
- data/ext/quadmath/internal/rb_quadmath.h +77 -0
- data/ext/quadmath/main.c +31 -0
- data/ext/quadmath/missing/cerfcq.c +158 -0
- data/ext/quadmath/missing/cerfq.c +35 -0
- data/ext/quadmath/missing/cl2norm2q.c +43 -0
- data/ext/quadmath/missing/clgammaq.c +61 -0
- data/ext/quadmath/missing/ctgammaq.c +56 -0
- data/ext/quadmath/missing/ool_quad2str.c +738 -0
- data/ext/quadmath/missing/opts_exception_p.c +20 -0
- data/ext/quadmath/numerable.c +2657 -0
- data/ext/quadmath/quadmath.c +2768 -0
- data/ext/quadmath/rb_quadmath.h +75 -0
- data/lib/quadmath/quadmath.so +0 -0
- data/lib/quadmath/version.rb +5 -0
- data/lib/quadmath.rb +8 -0
- data/pkg/quadmath-0.1.0.gem +0 -0
- data/sig/ruby/quadmath.rbs +6 -0
- metadata +70 -0
|
@@ -0,0 +1,494 @@
|
|
|
1
|
+
/*******************************************************************************
|
|
2
|
+
complex128.c -- Complex128 Class
|
|
3
|
+
|
|
4
|
+
Author: Hironobu Inatsuka
|
|
5
|
+
*******************************************************************************/
|
|
6
|
+
#include <ruby.h>
|
|
7
|
+
#include <quadmath.h>
|
|
8
|
+
#include "rb_quadmath.h"
|
|
9
|
+
#include "internal/rb_quadmath.h"
|
|
10
|
+
|
|
11
|
+
char ool_quad2str(__float128 x, char format, int *exp, int *sign, char **buf);
|
|
12
|
+
|
|
13
|
+
struct C128 { __complex128 value; } ;
|
|
14
|
+
|
|
15
|
+
static void
|
|
16
|
+
free_complex128(void *v)
|
|
17
|
+
{
|
|
18
|
+
if (v != NULL)
|
|
19
|
+
{
|
|
20
|
+
xfree(v);
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
static size_t
|
|
25
|
+
memsize_complex128(const void *_)
|
|
26
|
+
{
|
|
27
|
+
return sizeof(struct C128);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
static const rb_data_type_t complex128_data_type = {
|
|
31
|
+
"complex128",
|
|
32
|
+
{0, free_complex128, memsize_complex128,},
|
|
33
|
+
0, 0,
|
|
34
|
+
RUBY_TYPED_FREE_IMMEDIATELY,
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
static VALUE
|
|
38
|
+
complex128_allocate(__complex128 x)
|
|
39
|
+
{
|
|
40
|
+
struct C128 *ptr = ruby_xcalloc(1, sizeof(struct C128));
|
|
41
|
+
VALUE obj;
|
|
42
|
+
ptr->value = x;
|
|
43
|
+
obj = TypedData_Wrap_Struct(rb_cComplex128, &complex128_data_type, ptr);
|
|
44
|
+
RB_OBJ_FREEZE(obj);
|
|
45
|
+
return obj;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
__complex128
|
|
49
|
+
GetC128(VALUE self)
|
|
50
|
+
{
|
|
51
|
+
struct C128 *c128;
|
|
52
|
+
|
|
53
|
+
TypedData_Get_Struct(self, struct C128, &complex128_data_type, c128);
|
|
54
|
+
|
|
55
|
+
return c128->value;
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
/*
|
|
59
|
+
* call-seq:
|
|
60
|
+
* hash -> Integer
|
|
61
|
+
*
|
|
62
|
+
* +self+のHash値を返す.
|
|
63
|
+
*
|
|
64
|
+
*/
|
|
65
|
+
static VALUE
|
|
66
|
+
complex128_hash(VALUE self)
|
|
67
|
+
{
|
|
68
|
+
struct C128 *c128;;
|
|
69
|
+
st_index_t hash;
|
|
70
|
+
|
|
71
|
+
TypedData_Get_Struct(self, struct C128, &complex128_data_type, c128);
|
|
72
|
+
|
|
73
|
+
hash = rb_memhash(c128, sizeof(struct C128));
|
|
74
|
+
|
|
75
|
+
return ST2FIX(hash);
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
/*
|
|
79
|
+
* call-seq:
|
|
80
|
+
* eql?(other) -> bool
|
|
81
|
+
*
|
|
82
|
+
* +self+と+other+が等しければ真を返す.
|
|
83
|
+
*/
|
|
84
|
+
static VALUE
|
|
85
|
+
complex128_eql_p(VALUE self, VALUE other)
|
|
86
|
+
{
|
|
87
|
+
__complex128 left_c128, right_c128;
|
|
88
|
+
|
|
89
|
+
if (CLASS_OF(other) != rb_cComplex128)
|
|
90
|
+
return Qfalse;
|
|
91
|
+
|
|
92
|
+
left_c128 = GetC128(self);
|
|
93
|
+
right_c128 = GetC128(other);
|
|
94
|
+
|
|
95
|
+
return left_c128 == right_c128 ? Qtrue : Qfalse;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
/*
|
|
99
|
+
* call-seq:
|
|
100
|
+
* infinite? -> nil | 1
|
|
101
|
+
*
|
|
102
|
+
* +self+が無限複素量であるかを確認する.実部・虚部がともに有限であればnilを,そうでなければ1を返す.
|
|
103
|
+
|
|
104
|
+
*/
|
|
105
|
+
static VALUE
|
|
106
|
+
complex128_infinite_p(VALUE self)
|
|
107
|
+
{
|
|
108
|
+
__complex128 c128 = GetC128(self);
|
|
109
|
+
|
|
110
|
+
return (isinfq(crealq(c128)) || isinfq(cimagq(c128))) ?
|
|
111
|
+
INT2FIX(1) : Qnil;
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
/*
|
|
115
|
+
* call-seq:
|
|
116
|
+
* finite? -> bool
|
|
117
|
+
*
|
|
118
|
+
* +self+の実部・虚部がともに有限であればtrueを,そうでなければfalseを返す.
|
|
119
|
+
|
|
120
|
+
*/
|
|
121
|
+
static VALUE
|
|
122
|
+
complex128_finite_p(VALUE self)
|
|
123
|
+
{
|
|
124
|
+
__complex128 c128 = GetC128(self);
|
|
125
|
+
__float128 real, imag;
|
|
126
|
+
|
|
127
|
+
real = crealq(c128); imag = cimagq(c128);
|
|
128
|
+
|
|
129
|
+
return (finiteq(real) && finiteq(imag)) ? Qtrue : Qfalse;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
static char
|
|
133
|
+
member_format(__float128 x, VALUE s)
|
|
134
|
+
{
|
|
135
|
+
char* str;
|
|
136
|
+
int exp, sign;
|
|
137
|
+
char format = ool_quad2str(fabsq(x), 'g', &exp, &sign, &str);
|
|
138
|
+
|
|
139
|
+
switch (format) {
|
|
140
|
+
case '0':
|
|
141
|
+
rb_raise(rb_eRuntimeError, "error occured in ool_quad2str()");
|
|
142
|
+
break;
|
|
143
|
+
case '1':
|
|
144
|
+
rb_str_concat(s, rb_sprintf("%s", str));
|
|
145
|
+
break;
|
|
146
|
+
case 'e':
|
|
147
|
+
rb_str_concat(s, rb_sprintf("%se%+d", str, exp));
|
|
148
|
+
break;
|
|
149
|
+
case 'f':
|
|
150
|
+
rb_str_concat(s, rb_sprintf("%s", str));
|
|
151
|
+
break;
|
|
152
|
+
default:
|
|
153
|
+
rb_raise(rb_eRuntimeError, "format error");
|
|
154
|
+
break;
|
|
155
|
+
}
|
|
156
|
+
return format;
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
static VALUE
|
|
160
|
+
f_format(VALUE self)
|
|
161
|
+
{
|
|
162
|
+
VALUE retval = rb_str_new(0,0);
|
|
163
|
+
__complex128 c128 = GetC128(self);
|
|
164
|
+
char format;
|
|
165
|
+
__float128 memb;
|
|
166
|
+
|
|
167
|
+
memb = crealq(c128);
|
|
168
|
+
if (signbitq(memb)) rb_str_cat2(retval, "-");
|
|
169
|
+
member_format(memb, retval);
|
|
170
|
+
|
|
171
|
+
memb = cimagq(c128);
|
|
172
|
+
rb_str_cat2(retval, !signbitq(memb) ? "+" : "-");
|
|
173
|
+
format = member_format(memb, retval);
|
|
174
|
+
if (format == '1') rb_str_cat2(retval, "*");
|
|
175
|
+
rb_str_cat2(retval, "i");
|
|
176
|
+
|
|
177
|
+
return retval;
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
/*
|
|
181
|
+
* call-seq:
|
|
182
|
+
* to_s -> String
|
|
183
|
+
*
|
|
184
|
+
* +self+をStringに変換する.
|
|
185
|
+
*/
|
|
186
|
+
static VALUE
|
|
187
|
+
complex128_to_s(VALUE self)
|
|
188
|
+
{
|
|
189
|
+
return f_format(self);
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
/*
|
|
193
|
+
* call-seq:
|
|
194
|
+
* inspect -> String
|
|
195
|
+
*
|
|
196
|
+
* +self+を(Re+Im)の形で見やすくする.
|
|
197
|
+
*/
|
|
198
|
+
static VALUE
|
|
199
|
+
complex128_inspect(VALUE self)
|
|
200
|
+
{
|
|
201
|
+
VALUE s;
|
|
202
|
+
|
|
203
|
+
s = rb_usascii_str_new2("(");
|
|
204
|
+
rb_str_concat(s, f_format(self));
|
|
205
|
+
rb_str_cat2(s, ")");
|
|
206
|
+
|
|
207
|
+
return s;
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
|
|
211
|
+
/*
|
|
212
|
+
* call-seq:
|
|
213
|
+
* to_i -> Integer
|
|
214
|
+
*
|
|
215
|
+
* +self+を整数にして返す.
|
|
216
|
+
* 虚部がゼロでない(すなわち虚数が現れている)ならRangeErrorが,
|
|
217
|
+
* 実部が非数か無限ならFloatDomainErrorが発生する.
|
|
218
|
+
*/
|
|
219
|
+
static VALUE
|
|
220
|
+
complex128_to_i(VALUE self)
|
|
221
|
+
{
|
|
222
|
+
__complex128 c128 = GetC128(self);
|
|
223
|
+
|
|
224
|
+
if (cimagq(c128) == 0)
|
|
225
|
+
{
|
|
226
|
+
__float128 real = crealq(c128);
|
|
227
|
+
if (FIXABLE(real))
|
|
228
|
+
return LONG2FIX((long)real);
|
|
229
|
+
else
|
|
230
|
+
{
|
|
231
|
+
VALUE f128 = rb_float128_cf128(real);
|
|
232
|
+
return rb_funcall(f128, rb_intern("to_i"), 0);
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
else
|
|
236
|
+
rb_raise(rb_eRangeError,
|
|
237
|
+
"can't convert %"PRIsVALUE" into %s",
|
|
238
|
+
rb_String(self), rb_class2name(rb_cInteger));
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
/*
|
|
242
|
+
* call-seq:
|
|
243
|
+
* to_f -> Float
|
|
244
|
+
*
|
|
245
|
+
* +self+をFloat型にして返す.
|
|
246
|
+
* 内部的にはいったん__float128型を取り出してdouble型にキャストしている.
|
|
247
|
+
* 虚部がゼロでない(すなわち虚数が現れている)ならRangeErrorが発生する.
|
|
248
|
+
*/
|
|
249
|
+
static VALUE
|
|
250
|
+
complex128_to_f(VALUE self)
|
|
251
|
+
{
|
|
252
|
+
__complex128 c128 = GetC128(self);
|
|
253
|
+
|
|
254
|
+
if (cimagq(c128) == 0)
|
|
255
|
+
return DBL2NUM((double)crealq(c128));
|
|
256
|
+
else
|
|
257
|
+
rb_raise(rb_eRangeError,
|
|
258
|
+
"can't convert %"PRIsVALUE" into %s",
|
|
259
|
+
rb_String(self), rb_class2name(rb_cFloat));
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
/*
|
|
263
|
+
* call-seq:
|
|
264
|
+
* to_f128 -> Float128
|
|
265
|
+
*
|
|
266
|
+
* +self+をFloat128型にして返す.
|
|
267
|
+
* 虚部がゼロでない(すなわち虚数が現れている)ならRangeErrorが発生する.
|
|
268
|
+
*/
|
|
269
|
+
static VALUE
|
|
270
|
+
complex128_to_f128(VALUE self)
|
|
271
|
+
{
|
|
272
|
+
__complex128 c128 = GetC128(self);
|
|
273
|
+
|
|
274
|
+
if (cimagq(c128) == 0)
|
|
275
|
+
return rb_float128_cf128(crealq(c128));
|
|
276
|
+
else
|
|
277
|
+
rb_raise(rb_eRangeError,
|
|
278
|
+
"can't convert %"PRIsVALUE" into %s",
|
|
279
|
+
rb_String(self), rb_class2name(rb_cFloat128));
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
/*
|
|
283
|
+
* call-seq:
|
|
284
|
+
* to_c -> Complex
|
|
285
|
+
*
|
|
286
|
+
* +self+をComplex型にして返す.
|
|
287
|
+
* 実部・虚部は取り出され,Complex型のメンバ変数としてフックされる.
|
|
288
|
+
*/
|
|
289
|
+
static VALUE
|
|
290
|
+
complex128_to_c(VALUE self)
|
|
291
|
+
{
|
|
292
|
+
__complex128 c128 = GetC128(self);
|
|
293
|
+
|
|
294
|
+
return rb_Complex(
|
|
295
|
+
rb_float128_cf128(crealq(c128)),
|
|
296
|
+
rb_float128_cf128(cimagq(c128)));
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
/*
|
|
300
|
+
* call-seq:
|
|
301
|
+
* to_c128 -> Complex128
|
|
302
|
+
*
|
|
303
|
+
* 常に+self+を返す.
|
|
304
|
+
*/
|
|
305
|
+
static VALUE
|
|
306
|
+
complex128_to_c128(VALUE self)
|
|
307
|
+
{
|
|
308
|
+
return self;
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
/*
|
|
312
|
+
* call-seq:
|
|
313
|
+
* real -> Float128
|
|
314
|
+
*
|
|
315
|
+
* +self+の実部を返す.型はFloat128である.
|
|
316
|
+
*/
|
|
317
|
+
static VALUE
|
|
318
|
+
complex128_real(VALUE self)
|
|
319
|
+
{
|
|
320
|
+
__complex128 c128 = GetC128(self);
|
|
321
|
+
|
|
322
|
+
return rb_float128_cf128(crealq(c128));
|
|
323
|
+
}
|
|
324
|
+
|
|
325
|
+
/*
|
|
326
|
+
* call-seq:
|
|
327
|
+
* imag -> Float128
|
|
328
|
+
* imaginary -> Float128
|
|
329
|
+
*
|
|
330
|
+
* +self+の虚部を返す.型はFloat128である.
|
|
331
|
+
*/
|
|
332
|
+
static VALUE
|
|
333
|
+
complex128_imag(VALUE self)
|
|
334
|
+
{
|
|
335
|
+
__complex128 c128 = GetC128(self);
|
|
336
|
+
|
|
337
|
+
return rb_float128_cf128(cimagq(c128));
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
/*
|
|
341
|
+
* call-seq:
|
|
342
|
+
* rect -> [Float128, Float128]
|
|
343
|
+
* rectangular -> [Float128, Float128]
|
|
344
|
+
*
|
|
345
|
+
* 実部と虚部を配列にして返す.
|
|
346
|
+
* 見た目はComplex型と変わりないが,成分はFloat128型のみなのが異なる.
|
|
347
|
+
*
|
|
348
|
+
* Complex128(3).rect # => [3.0, 0.0]
|
|
349
|
+
* Complex128(3.5).rect # => [3.5, 0.0]
|
|
350
|
+
* Complex128(3, 2).rect # => [3.0, 2.0]
|
|
351
|
+
* Complex128(1, 1).rect.all?(Float128) # => true
|
|
352
|
+
*/
|
|
353
|
+
static VALUE
|
|
354
|
+
complex128_rect(VALUE self)
|
|
355
|
+
{
|
|
356
|
+
__complex128 c128 = GetC128(self);
|
|
357
|
+
|
|
358
|
+
return rb_assoc_new(
|
|
359
|
+
rb_float128_cf128(crealq(c128)),
|
|
360
|
+
rb_float128_cf128(cimagq(c128)));
|
|
361
|
+
}
|
|
362
|
+
|
|
363
|
+
/*
|
|
364
|
+
* call-seq:
|
|
365
|
+
* real? -> false
|
|
366
|
+
*
|
|
367
|
+
* 常にfalseを返す.
|
|
368
|
+
*/
|
|
369
|
+
static VALUE
|
|
370
|
+
complex128_real_p(VALUE self)
|
|
371
|
+
{
|
|
372
|
+
return Qfalse;
|
|
373
|
+
}
|
|
374
|
+
|
|
375
|
+
|
|
376
|
+
#if 0
|
|
377
|
+
static VALUE
|
|
378
|
+
complex128_initialize_copy(VALUE self, VALUE other)
|
|
379
|
+
{
|
|
380
|
+
struct C128 *pv = rb_check_typeddata(self, &complex128_data_type);
|
|
381
|
+
struct C128 *x = rb_check_typeddata(other, &complex128_data_type);
|
|
382
|
+
|
|
383
|
+
if (self != other)
|
|
384
|
+
{
|
|
385
|
+
pv->value = x->value;
|
|
386
|
+
}
|
|
387
|
+
return self;
|
|
388
|
+
}
|
|
389
|
+
#endif
|
|
390
|
+
|
|
391
|
+
/*
|
|
392
|
+
* call-seq:
|
|
393
|
+
* to_c64 -> Complex
|
|
394
|
+
*
|
|
395
|
+
* +self+を二倍精度に精度引き下げしてこれをComplexに変換し返す.
|
|
396
|
+
*
|
|
397
|
+
* QuadMath.asin(1.1r).to_c64 # => (1.5707963267948966+0.4435682543851152i)
|
|
398
|
+
*/
|
|
399
|
+
static VALUE
|
|
400
|
+
complex128_to_c64(VALUE self)
|
|
401
|
+
{
|
|
402
|
+
__complex128 c128 = GetC128(self);
|
|
403
|
+
return rb_dbl_complex_new((double)crealq(c128), (double)cimagq(c128));
|
|
404
|
+
}
|
|
405
|
+
|
|
406
|
+
static VALUE
|
|
407
|
+
f128_to_f64(VALUE obj)
|
|
408
|
+
{
|
|
409
|
+
__float128 elem = GetF128(obj);
|
|
410
|
+
return DBL2NUM((double)elem);
|
|
411
|
+
}
|
|
412
|
+
|
|
413
|
+
/*
|
|
414
|
+
* call-seq:
|
|
415
|
+
* to_c64 -> Complex
|
|
416
|
+
*
|
|
417
|
+
* +self+の成分が四倍精度の場合,二倍精度に精度引き下げして返す.
|
|
418
|
+
*
|
|
419
|
+
* z = Complex(3.to_f128) # => (3.0+0i)
|
|
420
|
+
* z.real.class # => Float128
|
|
421
|
+
* z.to_c64.real.class # => Float
|
|
422
|
+
|
|
423
|
+
*/
|
|
424
|
+
static VALUE
|
|
425
|
+
nucomp_to_c64(VALUE self)
|
|
426
|
+
{
|
|
427
|
+
VALUE real = rb_complex_real(self);
|
|
428
|
+
VALUE imag = rb_complex_imag(self);
|
|
429
|
+
|
|
430
|
+
if (CLASS_OF(real) == rb_cFloat128)
|
|
431
|
+
real = f128_to_f64(real);
|
|
432
|
+
if (CLASS_OF(imag) == rb_cFloat128)
|
|
433
|
+
imag = f128_to_f64(imag);
|
|
434
|
+
|
|
435
|
+
return rb_Complex(real, imag);
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
|
|
439
|
+
void
|
|
440
|
+
InitVM_Complex128(void)
|
|
441
|
+
{
|
|
442
|
+
/* Class methods */
|
|
443
|
+
rb_undef_alloc_func(rb_cComplex128);
|
|
444
|
+
rb_undef_method(CLASS_OF(rb_cComplex128), "new");
|
|
445
|
+
|
|
446
|
+
/* Object methods */
|
|
447
|
+
rb_define_method(rb_cComplex128, "hash", complex128_hash, 0);
|
|
448
|
+
rb_define_method(rb_cComplex128, "eql?", complex128_eql_p, 1);
|
|
449
|
+
|
|
450
|
+
/* The unique methods */
|
|
451
|
+
rb_define_method(rb_cComplex128, "real?", complex128_real_p, 0);
|
|
452
|
+
rb_define_method(rb_cComplex128, "real", complex128_real, 0);
|
|
453
|
+
rb_define_method(rb_cComplex128, "imag", complex128_imag, 0);
|
|
454
|
+
rb_define_alias(rb_cComplex128, "imaginary", "imag");
|
|
455
|
+
rb_define_method(rb_cComplex128, "rect", complex128_rect, 0);
|
|
456
|
+
rb_define_alias(rb_cComplex128, "rectangular", "rect");
|
|
457
|
+
rb_undef_method(rb_cComplex128, "i");
|
|
458
|
+
rb_define_method(rb_cComplex128, "infinite?", complex128_infinite_p, 0);
|
|
459
|
+
rb_define_method(rb_cComplex128, "finite?", complex128_finite_p, 0);
|
|
460
|
+
|
|
461
|
+
/* Type convertion methods */
|
|
462
|
+
rb_define_method(rb_cComplex128, "to_s", complex128_to_s, 0);
|
|
463
|
+
rb_define_method(rb_cComplex128, "inspect", complex128_inspect, 0);
|
|
464
|
+
|
|
465
|
+
rb_define_method(rb_cComplex128, "to_f", complex128_to_f, 0);
|
|
466
|
+
rb_define_method(rb_cComplex128, "to_f128", complex128_to_f128, 0);
|
|
467
|
+
|
|
468
|
+
rb_define_method(rb_cComplex128, "to_i", complex128_to_i, 0);
|
|
469
|
+
rb_define_method(rb_cComplex128, "to_int", complex128_to_i, 0);
|
|
470
|
+
|
|
471
|
+
rb_define_method(rb_cComplex128, "to_c", complex128_to_c, 0);
|
|
472
|
+
rb_define_method(rb_cComplex128, "to_c128", complex128_to_c128, 0);
|
|
473
|
+
|
|
474
|
+
rb_define_method(rb_cComplex128, "to_c64", complex128_to_c64, 0);
|
|
475
|
+
rb_define_method(rb_cComplex, "to_c64", nucomp_to_c64, 0);
|
|
476
|
+
|
|
477
|
+
/* Constants */
|
|
478
|
+
rb_define_const(rb_cComplex128, "I", rb_complex128_cc128(0+1i));
|
|
479
|
+
}
|
|
480
|
+
|
|
481
|
+
VALUE
|
|
482
|
+
rb_complex128_cc128(__complex128 x)
|
|
483
|
+
{
|
|
484
|
+
VALUE obj = complex128_allocate(x);
|
|
485
|
+
return obj;
|
|
486
|
+
}
|
|
487
|
+
|
|
488
|
+
__complex128
|
|
489
|
+
rb_complex128_value(VALUE x)
|
|
490
|
+
{
|
|
491
|
+
struct C128 *c128 = rb_check_typeddata(x, &complex128_data_type);
|
|
492
|
+
|
|
493
|
+
return c128->value;
|
|
494
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
require 'mkmf'
|
|
2
|
+
|
|
3
|
+
if have_header('quadmath.h')
|
|
4
|
+
have_func('rb_opts_exception_p', 'ruby.h')
|
|
5
|
+
have_func('cerfq', 'quadmath.h')
|
|
6
|
+
have_func('cerfcq', 'quadmath.h')
|
|
7
|
+
have_func('clgammaq', 'quadmath.h')
|
|
8
|
+
have_func('ctgammaq', 'quadmath.h')
|
|
9
|
+
have_func('cl2norm2q', 'quadmath.h')
|
|
10
|
+
|
|
11
|
+
$libs << " -lquadmath"
|
|
12
|
+
create_makefile('quadmath/quadmath')
|
|
13
|
+
else
|
|
14
|
+
$stderr.puts "quadmath not found"
|
|
15
|
+
end
|