From: Colin Bartlett Date: 2009-12-22T10:16:12+09:00 Subject: Re: Correcting complex math On Sun, Dec 20, 2009 at 9:10 PM, jzakiya wrote: > I see in Python % is invalid for complex numbers. > http://www.webreference.com/programming/python/ > http://docs.python.org/reference/expressions.html Yes. And < and > are also invalid for complex numbers, at least in Python 3.1. (I don't use Python, but I've set up Python 3.1 on my computer to see how it deals with complex numbers and other arithmetic.) So Ruby (from 1.9) and Python have a measure of agreement on what you shouldn't do with complex numbers. Interestingly, in Python 3.1: 8 ** (1/3) #=> 2.0 -8 ** (1/3) #=> 2.0; as in Ruby, it's evaluated as -(8 ** (1/3)) (-8) ** (1/3) #=> (1.0000000000000002+1.7320508075688772j) -2 * -2 * -2 #=> -8 (-1) ** (1/3) #=> (0.5000000000000001+0.8660254037844386j) It seems that what Python is doing is to calculate the "first" n'th root as (in polar coordinates) exp( i * theta / n ), with 0 <= theta < 2 * pi. That seems to be a reasonably good and (sort of) consistent rule: for positive real numbers you get the "positive" real root, and it works for non-integer n. And for negative real numbers and integer n you can generate the remaining roots from the first. But: I'm not sure I agree with the "automatic" conversion from reals to complex numbers. (There may be a way to disable that?) And there's a sort of inconsistency between being able to generate all the roots for the roots of negative real numbers, but not being able to do that for the roots of positive real numbers. Back to Ruby: bearing in mind this from July 2009 http://osdir.com/ml/ruby-core/2009-08/msg00083.html "About An Imaginary Number Literal (Translation)" ... "Matz supposes there must be someone who use complex numbers often" ... if I'm going to make comments about complex numbers when, to be honest, I only use them for fun, and then only infrequently, I had better state my qualifications (and lack of them) for doing so. A degree in Mathematics completed in 1973: I understood the arithmetic of complex numbers, but not the real meaning of complex differentiation and integration. About 5 years ago I got interested again (at an elementary, not an advanced, level) and I recommend "Visual Complex Analysis" by Tristram Needham. http://www.usfca.edu/vca/ "to replace our rich visual intuition by silly games with 2 x 2 matrices has always seemed to me to be the height of folly. It is therefore a special pleasure to see Visual Complex Analysis with its elegantly illustrated visual approach. Yes, he has 2 x 2 matrices—but his are interesting." Ian Stewart, NEW SCIENTIST [Ian Stewart is a *real* mathematician!] Summarising, if only for my benefit, are the following correct? 1. For both real and complex numbers (whether purely imaginary, mixed real and imaginary, or with a zero imaginary part) the positive n'th root of the absolute magnitude is a unique value for non-zero values of n, n being a non-zero integer or real number. (For negative n, the n'th root of v is (1/v)**(-1/n) ?) 2. Where n is a non-zero integer, and r is a real number > 0, then * if n is odd, there is a unique real (and positive) n'th root; * if n is even, there are two real n'th roots, one positive, one negative; 3. Where n is a non-zero integer, and r is a real number < 0, then * if n is odd, there is a unique real (and negative) n'th root; * if n is even, there is no real n'th root. 4. Where n is a non-zero integer, and c is a complex number != 0 (regarding any numbers with a zero imaginary part as complex) there are n.abs complex roots, all having the same absolute value. 5. Working with complex numbers, a reasonable calculation of a "first" n'th root, where n is integer or non-integer, is in polar coordinates r ** (1/n) * exp( i * theta / n ), where 0 < theta <= 2 * pi; for integer n, that generates the remaining n'th roots. After a quick look at your example implementation: in the method "roots", near the start, maybe insert something like: raise "roots some text: n not an integer" unless n.kind_of?(Integer) And for consistency in roots maybe return [self] if n == 1 ? As an afterthought, if one is *not* working with complex numbers, in what sort of calculations might one want an n'th root of a negative number?