summaryrefslogtreecommitdiff
path: root/complex.c
diff options
context:
space:
mode:
Diffstat (limited to 'complex.c')
-rw-r--r--complex.c374
1 files changed, 207 insertions, 167 deletions
diff --git a/complex.c b/complex.c
index 4d7dc2901c..78593bd155 100644
--- a/complex.c
+++ b/complex.c
@@ -21,11 +21,10 @@
VALUE rb_cComplex;
-static ID id_Unify, id_abs, id_abs2, id_arg, id_cmp, id_conjugate,
- id_convert, id_denominator, id_divmod, id_equal_p, id_exact_p, id_expt,
- id_floor, id_format, id_idiv, id_inspect, id_negate, id_new, id_new_bang,
- id_numerator, id_polar, id_quo, id_scalar_p, id_to_f, id_to_i, id_to_r,
- id_to_s, id_truncate;
+static ID id_Unify, id_abs, id_abs2, id_arg, id_cmp, id_conj, id_convert,
+ id_denominator, id_divmod, id_equal_p, id_expt, id_floor, id_hash,
+ id_idiv, id_inspect, id_negate, id_numerator, id_polar, id_quo,
+ id_real_p, id_to_f, id_to_i, id_to_r, id_to_s;
#define f_boolcast(x) ((x) ? Qtrue : Qfalse)
@@ -64,13 +63,17 @@ m_##n(VALUE x, VALUE y)\
return rb_funcall(rb_mMath, id_##n, 2, x, y);\
}
+#define PRESERVE_SIGNEDZERO
+
inline static VALUE
f_add(VALUE x, VALUE y)
{
+#ifndef PRESERVE_SIGNEDZERO
if (FIXNUM_P(y) && FIX2LONG(y) == 0)
return x;
else if (FIXNUM_P(x) && FIX2LONG(x) == 0)
return y;
+#endif
return rb_funcall(x, '+', 1, y);
}
@@ -117,6 +120,7 @@ binop(mod, '%')
inline static VALUE
f_mul(VALUE x, VALUE y)
{
+#ifndef PRESERVE_SIGNEDZERO
if (FIXNUM_P(y)) {
long iy = FIX2LONG(y);
if (iy == 0) {
@@ -135,14 +139,17 @@ f_mul(VALUE x, VALUE y)
else if (ix == 1)
return y;
}
+#endif
return rb_funcall(x, '*', 1, y);
}
inline static VALUE
f_sub(VALUE x, VALUE y)
{
+#ifndef PRESERVE_SIGNEDZERO
if (FIXNUM_P(y) && FIX2LONG(y) == 0)
return x;
+#endif
return rb_funcall(x, '-', 1, y);
}
@@ -151,23 +158,20 @@ binop(xor, '^')
fun1(abs)
fun1(abs2)
fun1(arg)
-fun1(conjugate)
+fun1(conj)
fun1(denominator)
-fun1(exact_p)
fun1(floor)
+fun1(hash)
fun1(inspect)
fun1(negate)
fun1(numerator)
fun1(polar)
-fun1(scalar_p)
-
-#define f_real_p f_scalar_p
+fun1(real_p)
fun1(to_f)
fun1(to_i)
fun1(to_r)
fun1(to_s)
-fun1(truncate)
fun2(divmod)
@@ -191,6 +195,8 @@ f_negative_p(VALUE x)
return rb_funcall(x, '<', 1, ZERO);
}
+#define f_positive_p(x) (!f_negative_p(x))
+
inline static VALUE
f_zero_p(VALUE x)
{
@@ -199,6 +205,8 @@ f_zero_p(VALUE x)
return rb_funcall(x, id_equal_p, 1, ZERO);
}
+#define f_nonzero_p(x) (!f_zero_p(x))
+
inline static VALUE
f_one_p(VALUE x)
{
@@ -243,6 +251,9 @@ k_complex_p(VALUE x)
return f_kind_of_p(x, rb_cComplex);
}
+#define k_exact_p(x) (!k_float_p(x))
+#define k_inexact_p(x) k_float_p(x)
+
#define get_dat1(x) \
struct RComplex *dat;\
dat = ((struct RComplex *)(x))
@@ -253,13 +264,13 @@ k_complex_p(VALUE x)
bdat = ((struct RComplex *)(y))
inline static VALUE
-nucomp_s_new_internal(VALUE klass, VALUE real, VALUE image)
+nucomp_s_new_internal(VALUE klass, VALUE real, VALUE imag)
{
NEWOBJ(obj, struct RComplex);
OBJSETUP(obj, klass, T_COMPLEX);
obj->real = real;
- obj->image = image;
+ obj->imag = imag;
return (VALUE)obj;
}
@@ -273,23 +284,23 @@ nucomp_s_alloc(VALUE klass)
static VALUE
nucomp_s_new_bang(int argc, VALUE *argv, VALUE klass)
{
- VALUE real, image;
+ VALUE real, imag;
- switch (rb_scan_args(argc, argv, "11", &real, &image)) {
+ switch (rb_scan_args(argc, argv, "11", &real, &imag)) {
case 1:
if (!k_numeric_p(real))
real = f_to_i(real);
- image = ZERO;
+ imag = ZERO;
break;
default:
if (!k_numeric_p(real))
real = f_to_i(real);
- if (!k_numeric_p(image))
- image = f_to_i(image);
+ if (!k_numeric_p(imag))
+ imag = f_to_i(imag);
break;
}
- return nucomp_s_new_internal(klass, real, image);
+ return nucomp_s_new_internal(klass, real, imag);
}
inline static VALUE
@@ -325,39 +336,38 @@ nucomp_real_check(VALUE num)
}
inline static VALUE
-nucomp_s_canonicalize_internal(VALUE klass, VALUE real, VALUE image)
+nucomp_s_canonicalize_internal(VALUE klass, VALUE real, VALUE imag)
{
#define CL_CANON
#ifdef CL_CANON
- if (f_zero_p(image) && f_unify_p(klass) &&
- !k_float_p(real) && !k_float_p(image))
+ if (f_zero_p(imag) && k_exact_p(imag) && f_unify_p(klass))
return real;
#else
- if (f_zero_p(image) && f_unify_p(klass))
+ if (f_zero_p(imag) && f_unify_p(klass))
return real;
#endif
- else if (f_real_p(real) && f_real_p(image))
- return nucomp_s_new_internal(klass, real, image);
+ else if (f_real_p(real) && f_real_p(imag))
+ return nucomp_s_new_internal(klass, real, imag);
else if (f_real_p(real)) {
- get_dat1(image);
+ get_dat1(imag);
return nucomp_s_new_internal(klass,
- f_sub(real, dat->image),
+ f_sub(real, dat->imag),
f_add(ZERO, dat->real));
}
- else if (f_real_p(image)) {
+ else if (f_real_p(imag)) {
get_dat1(real);
return nucomp_s_new_internal(klass,
dat->real,
- f_add(dat->image, image));
+ f_add(dat->imag, imag));
}
else {
- get_dat2(real, image);
+ get_dat2(real, imag);
return nucomp_s_new_internal(klass,
- f_sub(adat->real, bdat->image),
- f_add(adat->image, bdat->real));
+ f_sub(adat->real, bdat->imag),
+ f_add(adat->imag, bdat->real));
}
}
@@ -365,36 +375,40 @@ nucomp_s_canonicalize_internal(VALUE klass, VALUE real, VALUE image)
static VALUE
nucomp_s_canonicalize(int argc, VALUE *argv, VALUE klass)
{
- VALUE real, image;
+ VALUE real, imag;
- switch (rb_scan_args(argc, argv, "11", &real, &image)) {
+ switch (rb_scan_args(argc, argv, "11", &real, &imag)) {
case 1:
- image = ZERO;
+ nucomp_real_check(real);
+ imag = ZERO;
+ break;
+ default:
+ nucomp_real_check(real);
+ nucomp_real_check(imag);
break;
}
- nucomp_real_check(real);
- nucomp_real_check(image);
-
- return nucomp_s_canonicalize_internal(klass, real, image);
+ return nucomp_s_canonicalize_internal(klass, real, imag);
}
#endif
static VALUE
nucomp_s_new(int argc, VALUE *argv, VALUE klass)
{
- VALUE real, image;
+ VALUE real, imag;
- switch (rb_scan_args(argc, argv, "11", &real, &image)) {
+ switch (rb_scan_args(argc, argv, "11", &real, &imag)) {
case 1:
- image = ZERO;
+ nucomp_real_check(real);
+ imag = ZERO;
+ break;
+ default:
+ nucomp_real_check(real);
+ nucomp_real_check(imag);
break;
}
- nucomp_real_check(real);
- nucomp_real_check(image);
-
- return nucomp_s_canonicalize_internal(klass, real, image);
+ return nucomp_s_canonicalize_internal(klass, real, imag);
}
inline static VALUE
@@ -446,44 +460,46 @@ m_log_bang(VALUE x)
static VALUE
m_cos(VALUE x)
{
- get_dat1(x);
-
if (f_real_p(x))
return m_cos_bang(x);
- return f_complex_new2(rb_cComplex,
- f_mul(m_cos_bang(dat->real),
- m_cosh_bang(dat->image)),
- f_mul(f_negate(m_sin_bang(dat->real)),
- m_sinh_bang(dat->image)));
+ {
+ get_dat1(x);
+ return f_complex_new2(rb_cComplex,
+ f_mul(m_cos_bang(dat->real),
+ m_cosh_bang(dat->imag)),
+ f_mul(f_negate(m_sin_bang(dat->real)),
+ m_sinh_bang(dat->imag)));
+ }
}
static VALUE
m_sin(VALUE x)
{
- get_dat1(x);
-
if (f_real_p(x))
return m_sin_bang(x);
- return f_complex_new2(rb_cComplex,
- f_mul(m_sin_bang(dat->real),
- m_cosh_bang(dat->image)),
- f_mul(m_cos_bang(dat->real),
- m_sinh_bang(dat->image)));
+ {
+ get_dat1(x);
+ return f_complex_new2(rb_cComplex,
+ f_mul(m_sin_bang(dat->real),
+ m_cosh_bang(dat->imag)),
+ f_mul(m_cos_bang(dat->real),
+ m_sinh_bang(dat->imag)));
+ }
}
static VALUE
m_sqrt(VALUE x)
{
if (f_real_p(x)) {
- if (!f_negative_p(x))
+ if (f_positive_p(x))
return m_sqrt_bang(x);
return f_complex_new2(rb_cComplex, ZERO, m_sqrt_bang(f_negate(x)));
}
else {
get_dat1(x);
- if (f_negative_p(dat->image))
- return f_conjugate(m_sqrt(f_conjugate(x)));
+ if (f_negative_p(dat->imag))
+ return f_conj(m_sqrt(f_conj(x)));
else {
VALUE a = f_abs(x);
return f_complex_new2(rb_cComplex,
@@ -517,30 +533,38 @@ nucomp_real(VALUE self)
}
static VALUE
-nucomp_image(VALUE self)
+nucomp_imag(VALUE self)
{
get_dat1(self);
- return dat->image;
+ return dat->imag;
+}
+
+static VALUE
+nucomp_negate(VALUE self)
+{
+ get_dat1(self);
+ return f_complex_new2(CLASS_OF(self),
+ f_negate(dat->real), f_negate(dat->imag));
}
static VALUE
nucomp_add(VALUE self, VALUE other)
{
if (k_complex_p(other)) {
- VALUE real, image;
+ VALUE real, imag;
get_dat2(self, other);
real = f_add(adat->real, bdat->real);
- image = f_add(adat->image, bdat->image);
+ imag = f_add(adat->imag, bdat->imag);
- return f_complex_new2(CLASS_OF(self), real, image);
+ return f_complex_new2(CLASS_OF(self), real, imag);
}
if (k_numeric_p(other) && f_real_p(other)) {
get_dat1(self);
return f_complex_new2(CLASS_OF(self),
- f_add(dat->real, other), dat->image);
+ f_add(dat->real, other), dat->imag);
}
return rb_num_coerce_bin(self, other, '+');
}
@@ -549,20 +573,20 @@ static VALUE
nucomp_sub(VALUE self, VALUE other)
{
if (k_complex_p(other)) {
- VALUE real, image;
+ VALUE real, imag;
get_dat2(self, other);
real = f_sub(adat->real, bdat->real);
- image = f_sub(adat->image, bdat->image);
+ imag = f_sub(adat->imag, bdat->imag);
- return f_complex_new2(CLASS_OF(self), real, image);
+ return f_complex_new2(CLASS_OF(self), real, imag);
}
if (k_numeric_p(other) && f_real_p(other)) {
get_dat1(self);
return f_complex_new2(CLASS_OF(self),
- f_sub(dat->real, other), dat->image);
+ f_sub(dat->real, other), dat->imag);
}
return rb_num_coerce_bin(self, other, '-');
}
@@ -571,23 +595,23 @@ static VALUE
nucomp_mul(VALUE self, VALUE other)
{
if (k_complex_p(other)) {
- VALUE real, image;
+ VALUE real, imag;
get_dat2(self, other);
real = f_sub(f_mul(adat->real, bdat->real),
- f_mul(adat->image, bdat->image));
- image = f_add(f_mul(adat->real, bdat->image),
- f_mul(adat->image, bdat->real));
+ f_mul(adat->imag, bdat->imag));
+ imag = f_add(f_mul(adat->real, bdat->imag),
+ f_mul(adat->imag, bdat->real));
- return f_complex_new2(CLASS_OF(self), real, image);
+ return f_complex_new2(CLASS_OF(self), real, imag);
}
if (k_numeric_p(other) && f_real_p(other)) {
get_dat1(self);
return f_complex_new2(CLASS_OF(self),
f_mul(dat->real, other),
- f_mul(dat->image, other));
+ f_mul(dat->imag, other));
}
return rb_num_coerce_bin(self, other, '*');
}
@@ -601,23 +625,23 @@ nucomp_div(VALUE self, VALUE other)
get_dat2(self, other);
if (TYPE(adat->real) == T_FLOAT ||
- TYPE(adat->image) == T_FLOAT ||
+ TYPE(adat->imag) == T_FLOAT ||
TYPE(bdat->real) == T_FLOAT ||
- TYPE(bdat->image) == T_FLOAT) {
- VALUE magn = m_hypot(bdat->real, bdat->image);
+ TYPE(bdat->imag) == T_FLOAT) {
+ VALUE magn = m_hypot(bdat->real, bdat->imag);
VALUE tmp = f_complex_new_bang2(CLASS_OF(self),
f_div(bdat->real, magn),
- f_div(bdat->image, magn));
- return f_div(f_mul(self, f_conjugate(tmp)), magn);
+ f_div(bdat->imag, magn));
+ return f_div(f_mul(self, f_conj(tmp)), magn);
}
- return f_div(f_mul(self, f_conjugate(other)), f_abs2(other));
+ return f_div(f_mul(self, f_conj(other)), f_abs2(other));
}
if (k_numeric_p(other) && f_real_p(other)) {
get_dat1(self);
return f_complex_new2(CLASS_OF(self),
f_div(dat->real, other),
- f_div(dat->image, other));
+ f_div(dat->imag, other));
}
return rb_num_coerce_bin(self, other, '/');
}
@@ -632,13 +656,13 @@ nucomp_fdiv(VALUE self, VALUE other)
return f_div(f_complex_new2(CLASS_OF(self),
f_to_f(dat->real),
- f_to_f(dat->image)), other);
+ f_to_f(dat->imag)), other);
}
static VALUE
nucomp_expt(VALUE self, VALUE other)
{
- if (f_zero_p(other))
+ if (k_exact_p(other) && f_zero_p(other))
return f_complex_new_bang1(CLASS_OF(self), ONE);
if (k_rational_p(other) && f_one_p(f_denominator(other)))
@@ -654,7 +678,7 @@ nucomp_expt(VALUE self, VALUE other)
theta = RARRAY_PTR(a)[1];
ore = dat->real;
- oim = dat->image;
+ oim = dat->imag;
nr = m_exp_bang(f_sub(f_mul(ore, m_log_bang(r)),
f_mul(oim, theta)));
ntheta = f_add(f_mul(theta, ore), f_mul(oim, m_log_bang(r)));
@@ -668,7 +692,7 @@ nucomp_expt(VALUE self, VALUE other)
z = x;
n = f_sub(other, ONE);
- while (!f_zero_p(n)) {
+ while (f_nonzero_p(n)) {
VALUE a;
while (a = f_divmod(n, TWO),
@@ -677,8 +701,8 @@ nucomp_expt(VALUE self, VALUE other)
x = f_complex_new2(CLASS_OF(self),
f_sub(f_mul(dat->real, dat->real),
- f_mul(dat->image, dat->image)),
- f_mul(f_mul(TWO, dat->real), dat->image));
+ f_mul(dat->imag, dat->imag)),
+ f_mul(f_mul(TWO, dat->real), dat->imag));
n = RARRAY_PTR(a)[0];
}
z = f_mul(z, x);
@@ -707,12 +731,12 @@ nucomp_equal_p(VALUE self, VALUE other)
get_dat2(self, other);
return f_boolcast(f_equal_p(adat->real, bdat->real) &&
- f_equal_p(adat->image, bdat->image));
+ f_equal_p(adat->imag, bdat->imag));
}
if (k_numeric_p(other) && f_real_p(other)) {
get_dat1(self);
- return f_boolcast(f_equal_p(dat->real, other) && f_zero_p(dat->image));
+ return f_boolcast(f_equal_p(dat->real, other) && f_zero_p(dat->imag));
}
return f_equal_p(other, self);
}
@@ -732,7 +756,7 @@ static VALUE
nucomp_abs(VALUE self)
{
get_dat1(self);
- return m_hypot(dat->real, dat->image);
+ return m_hypot(dat->real, dat->imag);
}
static VALUE
@@ -740,21 +764,21 @@ nucomp_abs2(VALUE self)
{
get_dat1(self);
return f_add(f_mul(dat->real, dat->real),
- f_mul(dat->image, dat->image));
+ f_mul(dat->imag, dat->imag));
}
static VALUE
nucomp_arg(VALUE self)
{
get_dat1(self);
- return m_atan2_bang(dat->image, dat->real);
+ return m_atan2_bang(dat->imag, dat->real);
}
static VALUE
nucomp_rect(VALUE self)
{
get_dat1(self);
- return rb_assoc_new(dat->real, dat->image);
+ return rb_assoc_new(dat->real, dat->imag);
}
static VALUE
@@ -764,10 +788,10 @@ nucomp_polar(VALUE self)
}
static VALUE
-nucomp_conjugate(VALUE self)
+nucomp_conj(VALUE self)
{
get_dat1(self);
- return f_complex_new2(CLASS_OF(self), dat->real, f_negate(dat->image));
+ return f_complex_new2(CLASS_OF(self), dat->real, f_negate(dat->imag));
}
#if 0
@@ -789,7 +813,7 @@ static VALUE
nucomp_exact_p(VALUE self)
{
get_dat1(self);
- return f_boolcast(f_exact_p(dat->real) && f_exact_p(dat->image));
+ return f_boolcast(f_exact_p(dat->real) && f_exact_p(dat->imag));
}
static VALUE
@@ -805,7 +829,7 @@ static VALUE
nucomp_denominator(VALUE self)
{
get_dat1(self);
- return rb_lcm(f_denominator(dat->real), f_denominator(dat->image));
+ return rb_lcm(f_denominator(dat->real), f_denominator(dat->imag));
}
static VALUE
@@ -819,15 +843,29 @@ nucomp_numerator(VALUE self)
return f_complex_new2(CLASS_OF(self),
f_mul(f_numerator(dat->real),
f_div(cd, f_denominator(dat->real))),
- f_mul(f_numerator(dat->image),
- f_div(cd, f_denominator(dat->image))));
+ f_mul(f_numerator(dat->imag),
+ f_div(cd, f_denominator(dat->imag))));
}
static VALUE
nucomp_hash(VALUE self)
{
get_dat1(self);
- return f_xor(dat->real, dat->image);
+ return f_xor(f_hash(dat->real), f_hash(dat->imag));
+}
+
+static VALUE
+nucomp_eql_p(VALUE self, VALUE other)
+{
+ if (k_complex_p(other)) {
+ get_dat2(self, other);
+
+ return f_boolcast((CLASS_OF(adat->real) == CLASS_OF(bdat->real)) &&
+ (CLASS_OF(adat->imag) == CLASS_OF(bdat->imag)) &&
+ f_equal_p(self, other));
+
+ }
+ return Qfalse;
}
#ifndef HAVE_SIGNBIT
@@ -869,12 +907,12 @@ nucomp_to_s(VALUE self)
get_dat1(self);
- impos = f_tpositive_p(dat->image);
+ impos = f_tpositive_p(dat->imag);
s = f_to_s(dat->real);
rb_str_cat2(s, !impos ? "-" : "+");
- rb_str_concat(s, f_to_s(f_abs(dat->image)));
+ rb_str_concat(s, f_to_s(f_abs(dat->imag)));
rb_str_cat2(s, "i");
return s;
@@ -887,13 +925,13 @@ nucomp_inspect(VALUE self)
get_dat1(self);
- impos = f_tpositive_p(dat->image);
+ impos = f_tpositive_p(dat->imag);
s = rb_str_new2("(");
rb_str_concat(s, f_inspect(dat->real));
rb_str_cat2(s, !impos ? "-" : "+");
- rb_str_concat(s, f_inspect(f_abs(dat->image)));
+ rb_str_concat(s, f_inspect(f_abs(dat->imag)));
rb_str_cat2(s, "i)");
return s;
@@ -902,8 +940,12 @@ nucomp_inspect(VALUE self)
static VALUE
nucomp_marshal_dump(VALUE self)
{
+ VALUE a;
get_dat1(self);
- return rb_assoc_new(dat->real, dat->image);
+
+ a = rb_assoc_new(dat->real, dat->imag);
+ rb_copy_generic_ivar(a, self);
+ return a;
}
static VALUE
@@ -911,7 +953,8 @@ nucomp_marshal_load(VALUE self, VALUE a)
{
get_dat1(self);
dat->real = RARRAY_PTR(a)[0];
- dat->image = RARRAY_PTR(a)[1];
+ dat->imag = RARRAY_PTR(a)[1];
+ rb_copy_generic_ivar(self, a);
return self;
}
@@ -951,7 +994,7 @@ nucomp_to_i(VALUE self)
{
get_dat1(self);
- if (k_float_p(dat->image) || !f_zero_p(dat->image)) {
+ if (k_inexact_p(dat->imag) || f_nonzero_p(dat->imag)) {
VALUE s = f_to_s(self);
rb_raise(rb_eRangeError, "can't convert %s into Integer",
StringValuePtr(s));
@@ -964,7 +1007,7 @@ nucomp_to_f(VALUE self)
{
get_dat1(self);
- if (k_float_p(dat->image) || !f_zero_p(dat->image)) {
+ if (k_inexact_p(dat->imag) || f_nonzero_p(dat->imag)) {
VALUE s = f_to_s(self);
rb_raise(rb_eRangeError, "can't convert %s into Float",
StringValuePtr(s));
@@ -977,7 +1020,7 @@ nucomp_to_r(VALUE self)
{
get_dat1(self);
- if (k_float_p(dat->image) || !f_zero_p(dat->image)) {
+ if (k_inexact_p(dat->imag) || f_nonzero_p(dat->imag)) {
VALUE s = f_to_s(self);
rb_raise(rb_eRangeError, "can't convert %s into Rational",
StringValuePtr(s));
@@ -1021,29 +1064,29 @@ make_patterns(void)
if (comp_pat0) return;
comp_pat0 = rb_reg_new(comp_pat0_source, sizeof comp_pat0_source - 1, 0);
- rb_global_variable(&comp_pat0);
+ rb_gc_register_mark_object(comp_pat0);
comp_pat1 = rb_reg_new(comp_pat1_source, sizeof comp_pat1_source - 1, 0);
- rb_global_variable(&comp_pat1);
+ rb_gc_register_mark_object(comp_pat1);
comp_pat2 = rb_reg_new(comp_pat2_source, sizeof comp_pat2_source - 1, 0);
- rb_global_variable(&comp_pat2);
+ rb_gc_register_mark_object(comp_pat2);
a_slash = rb_str_new2("/");
- rb_global_variable(&a_slash);
+ rb_gc_register_mark_object(a_slash);
a_dot_and_an_e = rb_str_new2(".eE");
- rb_global_variable(&a_dot_and_an_e);
+ rb_gc_register_mark_object(a_dot_and_an_e);
null_string = rb_str_new2("");
- rb_global_variable(&null_string);
+ rb_gc_register_mark_object(null_string);
underscores_pat = rb_reg_new(underscores_pat_source,
sizeof underscores_pat_source - 1, 0);
- rb_global_variable(&underscores_pat);
+ rb_gc_register_mark_object(underscores_pat);
an_underscore = rb_str_new2("_");
- rb_global_variable(&an_underscore);
+ rb_gc_register_mark_object(an_underscore);
}
#define id_match rb_intern("match")
@@ -1109,9 +1152,8 @@ string_to_c_internal(VALUE self)
}
if (NIL_P(m)) {
m = f_match(comp_pat2, s);
- if (NIL_P(m)) {
+ if (NIL_P(m))
return rb_assoc_new(Qnil, self);
- }
sr = f_aref(m, INT2FIX(1));
if (NIL_P(f_aref(m, INT2FIX(2))))
si = Qnil;
@@ -1149,7 +1191,6 @@ string_to_c_internal(VALUE self)
return rb_assoc_new(rb_complex_polar(r, i), re);
else
return rb_assoc_new(rb_complex_new2(r, i), re);
-
}
}
@@ -1191,7 +1232,7 @@ nucomp_s_convert(int argc, VALUE *argv, VALUE klass)
{
VALUE a1, a2, backref;
- rb_scan_args(argc, argv, "02", &a1, &a2);
+ rb_scan_args(argc, argv, "11", &a1, &a2);
backref = rb_backref_get();
rb_match_busy(backref);
@@ -1223,7 +1264,7 @@ nucomp_s_convert(int argc, VALUE *argv, VALUE klass)
{
get_dat1(a1);
- if (!k_float_p(dat->image) && f_zero_p(dat->image))
+ if (k_exact_p(dat->imag) && f_zero_p(dat->imag))
a1 = dat->real;
}
}
@@ -1233,17 +1274,29 @@ nucomp_s_convert(int argc, VALUE *argv, VALUE klass)
{
get_dat1(a2);
- if (!k_float_p(dat->image) && f_zero_p(dat->image))
+ if (k_exact_p(dat->imag) && f_zero_p(dat->imag))
a2 = dat->real;
}
}
switch (TYPE(a1)) {
case T_COMPLEX:
- if (NIL_P(a2) || f_zero_p(a2))
+ if (argc == 1 || (k_exact_p(a2) && f_zero_p(a2)))
return a1;
}
+ if (argc == 1) {
+ if (k_numeric_p(a1) && !f_real_p(a1))
+ return a1;
+ }
+ else {
+ if ((k_numeric_p(a1) && k_numeric_p(a2)) &&
+ (!f_real_p(a1) || !f_real_p(a2)))
+ return f_add(a1,
+ f_mul(a2,
+ f_complex_new_bang2(rb_cComplex, ZERO, ONE)));
+ }
+
{
VALUE argv2[2];
argv2[0] = a1;
@@ -1254,20 +1307,6 @@ nucomp_s_convert(int argc, VALUE *argv, VALUE klass)
/* --- */
-#define id_Complex rb_intern("Complex")
-
-static VALUE
-numeric_re(VALUE self)
-{
- return rb_Complex1(self);
-}
-
-static VALUE
-numeric_im(VALUE self)
-{
- return rb_Complex2(ZERO, self);
-}
-
static VALUE
numeric_real(VALUE self)
{
@@ -1275,7 +1314,7 @@ numeric_real(VALUE self)
}
static VALUE
-numeric_image(VALUE self)
+numeric_imag(VALUE self)
{
return INT2FIX(0);
}
@@ -1291,7 +1330,7 @@ numeric_abs2(VALUE self)
static VALUE
numeric_arg(VALUE self)
{
- if (!f_negative_p(self))
+ if (f_positive_p(self))
return INT2FIX(0);
return rb_const_get(rb_mMath, id_PI);
}
@@ -1299,7 +1338,7 @@ numeric_arg(VALUE self)
static VALUE
numeric_rect(VALUE self)
{
- return rb_assoc_new(self, ZERO);
+ return rb_assoc_new(self, INT2FIX(0));
}
static VALUE
@@ -1309,7 +1348,7 @@ numeric_polar(VALUE self)
}
static VALUE
-numeric_conjugate(VALUE self)
+numeric_conj(VALUE self)
{
return self;
}
@@ -1327,29 +1366,25 @@ Init_Complex(void)
id_abs2 = rb_intern("abs2");
id_arg = rb_intern("arg");
id_cmp = rb_intern("<=>");
- id_conjugate = rb_intern("conjugate");
+ id_conj = rb_intern("conj");
id_convert = rb_intern("convert");
id_denominator = rb_intern("denominator");
id_divmod = rb_intern("divmod");
id_equal_p = rb_intern("==");
- id_exact_p = rb_intern("exact?");
id_expt = rb_intern("**");
id_floor = rb_intern("floor");
- id_format = rb_intern("format");
+ id_hash = rb_intern("hash");
id_idiv = rb_intern("div");
id_inspect = rb_intern("inspect");
id_negate = rb_intern("-@");
- id_new = rb_intern("new");
- id_new_bang = rb_intern("new!");
id_numerator = rb_intern("numerator");
id_polar = rb_intern("polar");
id_quo = rb_intern("quo");
- id_scalar_p = rb_intern("scalar?");
+ id_real_p = rb_intern("real?");
id_to_f = rb_intern("to_f");
id_to_i = rb_intern("to_i");
id_to_r = rb_intern("to_r");
id_to_s = rb_intern("to_s");
- id_truncate = rb_intern("truncate");
rb_cComplex = rb_define_class(COMPLEX_NAME, rb_cNumeric);
@@ -1390,9 +1425,10 @@ Init_Complex(void)
#endif
rb_define_method(rb_cComplex, "real", nucomp_real, 0);
- rb_define_method(rb_cComplex, "image", nucomp_image, 0);
- rb_define_method(rb_cComplex, "imag", nucomp_image, 0);
+ rb_define_method(rb_cComplex, "imaginary", nucomp_imag, 0);
+ rb_define_method(rb_cComplex, "imag", nucomp_imag, 0);
+ rb_define_method(rb_cComplex, "-@", nucomp_negate, 0);
rb_define_method(rb_cComplex, "+", nucomp_add, 1);
rb_define_method(rb_cComplex, "-", nucomp_sub, 1);
rb_define_method(rb_cComplex, "*", nucomp_mul, 1);
@@ -1413,24 +1449,24 @@ Init_Complex(void)
rb_define_method(rb_cComplex, "rectangular", nucomp_rect, 0);
rb_define_method(rb_cComplex, "rect", nucomp_rect, 0);
rb_define_method(rb_cComplex, "polar", nucomp_polar, 0);
- rb_define_method(rb_cComplex, "conjugate", nucomp_conjugate, 0);
- rb_define_method(rb_cComplex, "conj", nucomp_conjugate, 0);
+ rb_define_method(rb_cComplex, "conjugate", nucomp_conj, 0);
+ rb_define_method(rb_cComplex, "conj", nucomp_conj, 0);
#if 0
- rb_define_method(rb_cComplex, "~", nucomp_conjugate, 0); /* gcc */
+ rb_define_method(rb_cComplex, "~", nucomp_conj, 0); /* gcc */
#endif
-#if 0
rb_define_method(rb_cComplex, "real?", nucomp_false, 0);
+#if 0
rb_define_method(rb_cComplex, "complex?", nucomp_true, 0);
rb_define_method(rb_cComplex, "exact?", nucomp_exact_p, 0);
rb_define_method(rb_cComplex, "inexact?", nucomp_inexact_p, 0);
#endif
- rb_define_method(rb_cComplex, "scalar?", nucomp_false, 0);
rb_define_method(rb_cComplex, "numerator", nucomp_numerator, 0);
rb_define_method(rb_cComplex, "denominator", nucomp_denominator, 0);
rb_define_method(rb_cComplex, "hash", nucomp_hash, 0);
+ rb_define_method(rb_cComplex, "eql?", nucomp_eql_p, 1);
rb_define_method(rb_cComplex, "to_s", nucomp_to_s, 0);
rb_define_method(rb_cComplex, "inspect", nucomp_inspect, 0);
@@ -1456,11 +1492,9 @@ Init_Complex(void)
/* --- */
- rb_define_method(rb_cNumeric, "re", numeric_re, 0);
- rb_define_method(rb_cNumeric, "im", numeric_im, 0);
rb_define_method(rb_cNumeric, "real", numeric_real, 0);
- rb_define_method(rb_cNumeric, "image", numeric_image, 0);
- rb_define_method(rb_cNumeric, "imag", numeric_image, 0);
+ rb_define_method(rb_cNumeric, "imaginary", numeric_imag, 0);
+ rb_define_method(rb_cNumeric, "imag", numeric_imag, 0);
rb_define_method(rb_cNumeric, "abs2", numeric_abs2, 0);
rb_define_method(rb_cNumeric, "arg", numeric_arg, 0);
rb_define_method(rb_cNumeric, "angle", numeric_arg, 0);
@@ -1468,9 +1502,15 @@ Init_Complex(void)
rb_define_method(rb_cNumeric, "rectangular", numeric_rect, 0);
rb_define_method(rb_cNumeric, "rect", numeric_rect, 0);
rb_define_method(rb_cNumeric, "polar", numeric_polar, 0);
- rb_define_method(rb_cNumeric, "conjugate", numeric_conjugate, 0);
- rb_define_method(rb_cNumeric, "conj", numeric_conjugate, 0);
+ rb_define_method(rb_cNumeric, "conjugate", numeric_conj, 0);
+ rb_define_method(rb_cNumeric, "conj", numeric_conj, 0);
rb_define_const(rb_cComplex, "I",
f_complex_new_bang2(rb_cComplex, ZERO, ONE));
}
+
+/*
+Local variables:
+c-file-style: "ruby"
+End:
+*/