Re: $foo[0][0] versus $foo[0;0]

2008-07-16 Thread Larry Wall
On Sun, Jul 13, 2008 at 02:17:10PM -0500, Adrian Kreher wrote:
: Hi,
: 
: I'm reviewing the tests in S09, and the file 
: t/spec/S02-builtin_data_types/multi_dimensional_array.t uses the [0][0]  
: indexing format interchangeably with [0;0].
: 
: These two formats mean two different things, correct? The [0][0] form isn't 
: mentioned much in the spec, nor is [0;0] or if they interact somehow.

I think they should come out to meaning the same thing, though the
[0][0] form may be less efficient if it has to temporarily construct
a slice of the next dimension of the array.  On the other hand, a
naïve implementation of the multidimensional subscripter might just do
the same thing internally for the semicolon, so it could be a wash.

Larry


Re: Complex planes

2008-07-16 Thread Larry Wall
On Tue, Jul 15, 2008 at 03:30:24PM +0200, Moritz Lenz wrote:
: Today bacek++ implement complex logarithms in rakudo, and one of the
: tests failed because it assumed the result to be on a different complex
: plane. (log(-1i) returned 0- 1.5708i, while 0 + 3/2*1i was expected).
: 
: Should we standardize on one complex plane (for example -pi = $c.angle
:  pi like Complex.angle does)? Or simply fix the test to be agnostic to
: complex planes?

Standardizing on one complex plane is the normal solution, though
this being Perl 6, there's probably a better solution using infinite
Junctions if we can assume them to be both sufficiently lazy and
sufficiently intelligent... :)

Larry


Re: meta_postfix:*

2008-07-16 Thread Larry Wall
On Sun, Jul 13, 2008 at 12:46:30PM +0200, TSa (Thomas Sandlaß) wrote:
: HaloO,
: 
: I know that the hot phase of the operator discussions are over.
: But here's a little orthogonalizing idea from my side. The observation
: is that * can be regarded as repeated addition: 5 * 3 == 5 + 5 + 5
: and ** as repeated multiplication. Now imagine having a meta_postfix:*
: that gives +* as multiplication (perhaps abbreviated as *) and ** as
: (integer) exponentiation. We can then continue with replication as ~*
: for strings and ,* for lists thus freeing x and xx as some generic
: multiplication operators.

I think this is not going to fly from the standpoint of keeping common
operators visually distinct.  Also, how will you parse 1..* and such?

(Another consideration is that every time you add another metaoperator
you're potentially exploding the number of operators that the longest
token matcher needs to deal with, though STD currently cheats on this.)

: The meta * also is useful e.g. as (1,2) Z* 3 === (1,1,1),(2,2,2). Also
: when we apply it to unary postfix as well: $x++* 3 === $x++.++.++ which
: is useful when $x is of some class with overloaded ++ where the single
: steps are important. The meta postfix * could also be stacked and tetration
: falls out naturally as ***.

Speaking on behalf of the mere mortal, My Eyes Glaze Over.

Speaking as a parser writer, you're confusing the parser with a
metaoperator that changes expectation of term vs infix.

Sepaking as a programmer, $x++.++.++ won't do what you seem to think it does.

: With + as the default case for meta_postfix:* we win the advantage that
: we have +* and * as multiplication operators with the latter being a special
: form of the former. But for Vectors +* would automatically yield the scalar
: multiplication infix:+*:(Vector,Num) when infix:+:(Vector,Vector) is
: defined as expected.

You can, of course, do anything you like with your own copy, but the
standard reserves most of Unicode as the playground of mathematicians,
so please leave our poor little * alone.  :)

Larry


Re: Complex planes

2008-07-16 Thread Jon Lang
Larry Wall wrote:
 On Tue, Jul 15, 2008 at 03:30:24PM +0200, Moritz Lenz wrote:
 : Today bacek++ implement complex logarithms in rakudo, and one of the
 : tests failed because it assumed the result to be on a different complex
 : plane. (log(-1i) returned 0- 1.5708i, while 0 + 3/2*1i was expected).
 :
 : Should we standardize on one complex plane (for example -pi = $c.angle
 :  pi like Complex.angle does)? Or simply fix the test to be agnostic to
 : complex planes?

 Standardizing on one complex plane is the normal solution, though
 this being Perl 6, there's probably a better solution using infinite
 Junctions if we can assume them to be both sufficiently lazy and
 sufficiently intelligent... :)

By the principle of least surprise, I'd recommend against this.  Most
programmers, when they see 'sqrt(1)', will expect a return value of 1,
and won't want to jump through the hurdles involved in picking '1' out
of 'any(1, -1)'.  That said, I'm not necessarily opposed to these
functions including something like an ':any' or ':all' adverb that
causes them to return a junction of all possible answers; but this
should be something that you have to explicitly ask for.

And even then, I'm concerned that it might very quickly get out of
hand.  Consider:

  pow(1, 1/pi() ) :any - 1

(I think I got that right...)

Since pi is an irrational number, there are infinitely many distinct
results to raising 1 to the power of 1/pi.  (All but one of them are
complex numbers, and all of them have a magnitude of 1, differing only
in their angles.)  Thus, pow(1, 1/pi() ) :any would have to return a
junction of an indefinitely long lazy list.  Now subtract 1 from that
junction.  Do you have to flatten the list in order to do so,
subtracting one from each item in the list?  Or is there a reasonable
way to modify the list generator to incorporate the subtraction?

Or how about:

  sqrt(1):any + sqrt(1):any

--

In any case, there's the matter of what to do when you only want one
answer, and not a junction of them.  IMHO, we should standardize the
angles on '-pi ^.. pi'.  My reasoning is as follows: if the imaginary
component is positive, the angle should be positive; if the imaginary
component is negative, the angle should be negative.  If the imaginary
component is zero and the real component is not negative, the angle
should be zero.  And the square root of -1 should be i, not -i; so if
the imaginary component is zero and the real component is negative,
the angle should be positive, not negative.

-- 
Jonathan Dataweaver Lang


Re: Complex planes

2008-07-16 Thread Moritz Lenz
Jon Lang wrote:
 Larry Wall wrote:
 On Tue, Jul 15, 2008 at 03:30:24PM +0200, Moritz Lenz wrote:
 : Today bacek++ implement complex logarithms in rakudo, and one of the
 : tests failed because it assumed the result to be on a different complex
 : plane. (log(-1i) returned 0- 1.5708i, while 0 + 3/2*1i was expected).
 :
 : Should we standardize on one complex plane (for example -pi = $c.angle
 :  pi like Complex.angle does)? Or simply fix the test to be agnostic to
 : complex planes?

 Standardizing on one complex plane is the normal solution, though
 this being Perl 6, there's probably a better solution using infinite
 Junctions if we can assume them to be both sufficiently lazy and
 sufficiently intelligent... :)
 
 By the principle of least surprise, I'd recommend against this.  Most
 programmers, when they see 'sqrt(1)', will expect a return value of 1,

And that's what they get unless they write it as sqrt(1 + 0i).

 and won't want to jump through the hurdles involved in picking '1' out
 of 'any(1, -1)'. 

1 and -1 aren't just separated by a complex plain, they are really
distinct numbers

 That said, I'm not necessarily opposed to these
 functions including something like an ':any' or ':all' adverb that
 causes them to return a junction of all possible answers; but this
 should be something that you have to explicitly ask for.
 
 And even then, I'm concerned that it might very quickly get out of
 hand.  Consider:
 
   pow(1, 1/pi() ) :any - 1
 
 (I think I got that right...)

Not quite. Afaict the only functions that might return a junction are
Complex.angle and Complex.log.

But having
   $compl.angle  pi
always yield True would be quite weird ;-)

 Since pi is an irrational number, there are infinitely many distinct
 results to raising 1 to the power of 1/pi.

No. exp($x) is a single, well-defined value.

  (All but one of them are
 complex numbers, and all of them have a magnitude of 1, differing only
 in their angles.)  Thus, pow(1, 1/pi() ) :any would have to return a
 junction of an indefinitely long lazy list.  Now subtract 1 from that
 junction.  Do you have to flatten the list in order to do so,
 subtracting one from each item in the list?  

Obviously we'd have to avoid that if there's any infinite list/junction
involved somewhere ;-)

But you do have a point that we can't really use infinite junctions
unless we can ensure that we can do all sorts of arithmetics with it
without loosing lazyness. And I don't think we can prove that (but I
might give it it shot if I have some spare time)

 Or is there a reasonable
 way to modify the list generator to incorporate the subtraction?
 
 Or how about:
 
   sqrt(1):any + sqrt(1):any
 
 --
 
 In any case, there's the matter of what to do when you only want one
 answer, and not a junction of them.  IMHO, we should standardize the
 angles on '-pi ^.. pi'.  My reasoning is as follows: if the imaginary
 component is positive, the angle should be positive; if the imaginary
 component is negative, the angle should be negative.  If the imaginary
 component is zero and the real component is not negative, the angle
 should be zero.  And the square root of -1 should be i, not -i; so if
 the imaginary component is zero and the real component is negative,
 the angle should be positive, not negative.
 


-- 
Moritz Lenz
http://moritz.faui2k3.org/ |  http://perl-6.de/


[svn:perl6-synopsis] r14563 - doc/trunk/design/syn

2008-07-16 Thread larry
Author: larry
Date: Wed Jul 16 12:56:34 2008
New Revision: 14563

Modified:
   doc/trunk/design/syn/S04.pod

Log:
[S04] another whack at defining consistent closure semantics


Modified: doc/trunk/design/syn/S04.pod
==
--- doc/trunk/design/syn/S04.pod(original)
+++ doc/trunk/design/syn/S04.podWed Jul 16 12:56:34 2008
@@ -12,9 +12,9 @@
 
   Maintainer: Larry Wall [EMAIL PROTECTED]
   Date: 19 Aug 2004
-  Last Modified: 12 July 2008
+  Last Modified: 16 July 2008
   Number: 4
-  Version: 66
+  Version: 67
 
 This document summarizes Apocalypse 4, which covers the block and
 statement syntax of Perl.
@@ -1253,27 +1253,64 @@
 is free to turn unreferenced closures into mere blocks of code.
 It is also free to turn referenced closures into mere anonymous
 subroutines if the block does not refer to any external lexicals that
-should themselves be cloned.  In particular, named subroutines in any
-scope do not consider themselves closures unless you take a reference
-to them.  So
+should themselves be cloned.  (When we say clone, we mean the way
+the system takes a snapshot of the routine's lexical scope and binds
+it to the current instance of the routine so that if you ever use
+the current reference to the routine, it gets the current snapshot
+of its world in terms of the lexical symbols that are visible to it.)
+
+All remaining blocks are conceptually cloned into closures as soon
+as the lexical scope containing them is entered.  (This may be done
+lazily as long as consistent semantics are preserved, so a block
+that is never executed and never has a reference taken can avoid
+cloning altogether.  Execution or reference taking forces cloning
+in this case--references are not allowed to be lazily cloned, since
+no guarantee can be made that the scope needed for cloning will
+remain in existence over the life of the reference.)
+
+In particular, named subroutines are a special problem when embedded in
+a changing lexical scope (when they make reference to it).  The binding
+of such a definition to a name within a symbol table counts as taking
+a reference, so at compile time there is an initial C::= binding
+to the symbol table entry in question.  For global bindings to
+symbol tables visible at compile time, this binds to the compile-time
+view of the lexical scopes.  (At run-time, the initial run-time view
+of these scopes is copied from the compiler's view of them, so that
+initializations carry over, for instance.)  At run time, whenever such
+a subroutine needs to be cloned, an additional C:= binding is done
+at clone time to the same symbol table entry that the original C::=
+was bound to.  (The binding is not restored on exit from the current
+lexical scope; this C:= binding records the Ilast cloning, not
+the currently in-use cloning, so any use of the global reference must
+take into consideration that it is functioning only as a cache of the
+most recent cloning, not as a surrogate for the current lexical scope.)
+
+Lexical names do not share this problem, since the symbol goes out
+of scope synchronously with its usage.  Unlike global subs, they
+do not need a compile-time C::= binding, but like global subs,
+they perform a C:= binding to the lexical symbol at clone time
+(again, conceptually at the entry to the outer lexical scope, but
+possible deferred.)
 
 sub foo {
+   # conceptual cloning happens to both blocks below
 my $x = 1;
-my sub bar { print $x } # not cloned yet
-my baz = { bar(); print $x };  # cloned immediately
-my $code = bar;# now bar is cloned
+my sub bar { print $x } # already conceptualy cloned, but can 
be lazily deferred
+my baz := { bar(); print $x }; # block is cloned immediately, forcing 
cloning of bar
+my $code = bar;# this would also force bar to be 
cloned
 return baz;
 }
 
-When we say clone, we mean the way the system takes a snapshot of the
-routine's lexical scope and binds it to the current instance of the routine
-so that if you ever use the current reference to the routine, it gets
-the current snapshot of its world, lexically speaking.  (When we say that
-named subroutines do not consider themselves closures, this is a bit of a
-fib, since we must, in fact, take a reference to the subroutine in order to
-store it into the symbol table!  But this operation happens at compile time
-so the lexical scopes in view are just the initial prototype lexical scopes
-visible to the compiler.)
+In particular, blocks of inline control flow need not be cloned until
+called.  [Note: this is currently a potential problem for user-defined
+constructs, since you have to take references to blocks to pass them
+to whatever is managing the control flow.  Perhaps the laziness can
+be deferred through Captures to binding time, so a slurpy of block
+refs doesn't clone them 

Re: Complex planes

2008-07-16 Thread Jon Lang
Moritz Lenz wrote:
 Jon Lang wrote:
 By the principle of least surprise, I'd recommend against this.  Most
 programmers, when they see 'sqrt(1)', will expect a return value of 1,

 And that's what they get unless they write it as sqrt(1 + 0i).

I suppose that you _could_ use the programmer's choice of whether or
not to use complex numbers in the argument list as the indicator of
whether to return one answer or a junction of them.  Of course, this
could lead to subtle bugs where the programmer assigns a complex value
to $x and later takes the sqrt($x), but forgets that he assigned a
complex number earlier.  This may or may not be sufficient grounds for
requiring an explicit declaration that you want junctions.

 and won't want to jump through the hurdles involved in picking '1' out
 of 'any(1, -1)'.

 1 and -1 aren't just separated by a complex plane, they are really
 distinct numbers

True enough.  I fail to see how that invalidates my point, though: if
you're going to mess with multiple complex planes, why wouldn't you
also address the issue of distinct numbers as well?  The latter issue
is intimately connected to the former, as I demonstrate below.

 And even then, I'm concerned that it might very quickly get out of
 hand.  Consider:

   pow(1, 1/pi() ) :any - 1

 (I think I got that right...)

 Not quite. Afaict the only functions that might return a junction are
 Complex.angle and Complex.log.

Why is that?  Complex numbers can exist on multiple complex planes
even if you don't explicitly look at the angle.  One example of this
phenomenon in action takes the form of a 'proof' that 1 == -1:

  1 == sqrt(1) == sqrt(-1 * -1) == sqrt(-1) * sqrt(-1) == i * i == -1
# Assumes complex numbers throughout. 

The equality between the first and second steps means that the 1
inside the sqrt can only have an angle that is a multiple of 4pi.
Because of this, the -1's that appear in the third step cannot exist
on the same complex plane with each other: e.g., if the first one has
an angle of pi, the second has to have an angle of -pi, 3pi, 7pi,
11pi, ...  As a result of this, the signs of the sqrts in the fourth
step must be opposed: if the first sqrt(-1) returns i, the second
sqrt(-1) must return -i, and vice versa.  That means that there's a
negative term missing in the fifth step, which would cancel out the
negative term that appears in the final step.  At the very least, we
need to add infix:** and all related functions (e.g., sqrt) to the
list of functions that might return a junction.

And when and if Perl 6 adds constraint programming to its repertoire,
it will have to be smart enough to properly constrain complex planes
as well as complex values.

--

Bringing this back down a bit closer to Earth: if you supply a complex
number using rectilinear coordinates, a case could be made that you've
provided insufficient information, and that the complex number ought
to be stored as a junction of all of the different complex plane
representations for that otherwise-distinct value.  If you supply a
complex number using polar coordinates, you have been able to supply
the choice of complex plane as well as a distinct value; so only one
representation should be stored.  That is:

  (1 + 0 * i).angle == any (0, 2 * pi, 4 * pi, ...);
  exp(0 * i).angle == 0;
  exp(2 * pi * i).angle == 2 * pi;

So:

  (1 + 0 * i) == any (exp(0), exp(2 * pi * i), exp(4 * pi * i), ...);

Extending this further: exp($C) effectively reinterprets a complex
number's rectilinear coordinates as polar coordinates, and log($C)
does the inverse.  So as long as $C contains a single value, exp($C)
should always return a complex number that exists on a single complex
plane, established by $C's imaginary component; conversely, log($C)
ought to return a complex value that is represented on every possible
complex plane, since neither the angle nor the magnitude of $C
provides enough information to determine which plane to use.

Of course, there may be (and probably are) technical difficulties that
make this unworkable.

 Since pi is an irrational number, there are infinitely many distinct
 results to raising 1 to the power of 1/pi.

 No. exp($x) is a single, well-defined value.

True, as long as $x is a single, well-defined value.

But I wasn't talking about exp($x); I was talking about pow($x, $y),
$x ** $y, sqrt($x), and so on.  Just as:

  sqrt(1 + 0 * i) == sqrt(any(exp(0), exp(2 * pi * i), exp(4 * pi *
i), ...)) == any(exp(0), exp(pi * i), exp(2 * pi * i), ...)

it is also the case that:

  (1 + 0 * i) ** pi == any(exp(0), exp(2 * pi * i), exp(4 * pi * i),
...) ** pi == any(exp(0), exp(2 * pi * pi * i), exp(4 * pi * pi * i),
...)

And all of those answers are distinct values.

 But you do have a point that we can't really use infinite junctions
 unless we can ensure that we can do all sorts of arithmetics with it
 without losing laziness. And I don't think we can prove that (but I
 might give it it shot if I have some spare time)

Just noting that we're 

Re: Complex planes

2008-07-16 Thread Moritz Lenz
Jon Lang wrote:
 Moritz Lenz wrote:
 Jon Lang wrote:
 By the principle of least surprise, I'd recommend against this.  Most
 programmers, when they see 'sqrt(1)', will expect a return value of 1,

 And that's what they get unless they write it as sqrt(1 + 0i).
 
 I suppose that you _could_ use the programmer's choice of whether or
 not to use complex numbers in the argument list as the indicator of
 whether to return one answer or a junction of them.  Of course, this
 could lead to subtle bugs where the programmer assigns a complex value
 to $x and later takes the sqrt($x), but forgets that he assigned a
 complex number earlier.  This may or may not be sufficient grounds for
 requiring an explicit declaration that you want junctions.

If the programmer errs on what he thinks is in a variable, it'll always
be a bug.

 and won't want to jump through the hurdles involved in picking '1' out
 of 'any(1, -1)'.

 1 and -1 aren't just separated by a complex plane, they are really
 distinct numbers
 
 True enough.  I fail to see how that invalidates my point, though: if
 you're going to mess with multiple complex planes, why wouldn't you
 also address the issue of distinct numbers as well? 

Principle of least surprise:

Suppose sqrt(1) returns any(1, -1):
if sqrt($x)  0.5 { do something }

I can see the big, fat WTF written in the face of programmer who tries
to debug that code, and doesn't know about junctions. It just won't DTRT.

 The latter issue
 is intimately connected to the former, as I demonstrate below.
 
 And even then, I'm concerned that it might very quickly get out of
 hand.  Consider:

   pow(1, 1/pi() ) :any - 1

 (I think I got that right...)

 Not quite. Afaict the only functions that might return a junction are
 Complex.angle and Complex.log.
 
 Why is that?  

As I pointed out above it's insane to return a junction of logically
distinct values. It might even be insane to do it for Complex.log:

my $a = (Num::e * 1i).log.angle;

What do you expect $a to be?

Let's see, 1i can be written as exp(1i*(1/2 + 2 *$k) * pi), for Int $k.
So log(Nom::e * 1i) would
1 + any(..., -1.5 * pi, 0.5 * pi, 2.5 * pi, 4.5*pi)*1i
if you imagine this, all these values have re = 1, and lie on a straight
line. So their angle are discrete (but not dense) values between -pi and
+pi. There' no way you can represent that in finite space without a fair
bit of algebra, something we don't want to burden on our implementors.
And somehow I also don't think that meets the principle of least
surprise criterion.

I think that I don't have to comment on the rest of the mail to make
clear that Larry's proposal, although being quite interesting, is a very
bad idea to actually implement (and very hard to implement as well)
(unless somebody comes to its rescue with a really clever idea on how to
resolve all these weirdnesses).

Cheers,
Moritz

-- 
Moritz Lenz
http://moritz.faui2k3.org/ |  http://perl-6.de/


Re: Complex planes

2008-07-16 Thread mark . a . biggar
Let's worry about getting principal values, branch cuts and handling signed 
zeros correct before dealing with the interaction of junctions and multi-valued 
complex functions.

--
Mark Biggar
[EMAIL PROTECTED]
[EMAIL PROTECTED]
[EMAIL PROTECTED]


Re: Complex planes

2008-07-16 Thread Jon Lang
Moritz Lenz wrote:
 If the programmer errs on what he thinks is in a variable, it'll always
 be a bug.

Yes; but some bugs are easier to make, and harder to catch, than others.

 Principle of least surprise:

 Suppose sqrt(1) returns any(1, -1):
 if sqrt($x)  0.5 { do something }

 I can see the big, fat WTF written in the face of programmer who tries
 to debug that code, and doesn't know about junctions. It just won't DTRT.

This is closely related to my original point.  In particular, if
you're unwilling to have sqrt return junctions of distinct values, you
don't really want to mess with junctions of a single complex value on
different planes, either.

 And even then, I'm concerned that it might very quickly get out of
 hand.  Consider:

   pow(1, 1/pi() ) :any - 1

 (I think I got that right...)

 Not quite. Afaict the only functions that might return a junction are
 Complex.angle and Complex.log.

 Why is that?

 As I pointed out above it's insane to return a junction of logically
 distinct values.

It's only insane if the programmer isn't expecting it - which goes
back to my first point of making sure that the programmer explicitly
asked for it before giving it to him.

 It might even be insane to do it for Complex.log:

Agreed: if you are uncomfortable with sqrt(1) returning a junction of
distinct values, then Complex.log should likewise not return a
junction of distinct values.

 I think that I don't have to comment on the rest of the mail to make
 clear that Larry's proposal, although being quite interesting, is a very
 bad idea to actually implement (and very hard to implement as well)
 (unless somebody comes to its rescue with a really clever idea on how to
 resolve all these weirdnesses).

Well... yes and no.  Remember, I started off by recommending against
Larry's proposal.  I haven't changed my mind, although I think that
it's worth exploring whether or not an alternate treatment of complex
numbers is doable.

-- 
Jonathan Dataweaver Lang


Re: [svn:perl6-synopsis] r14563 - doc/trunk/design/syn

2008-07-16 Thread Brandon S. Allbery KF8NH

Minor typo:

On 2008 Jul 16, at 15:56, [EMAIL PROTECTED] wrote:


+(again, conceptually at the entry to the outer lexical scope, but
+possible deferred.)

sub foo {


possibly

--
brandon s. allbery [solaris,freebsd,perl,pugs,haskell] [EMAIL PROTECTED]
system administrator [openafs,heimdal,too many hats] [EMAIL PROTECTED]
electrical and computer engineering, carnegie mellon universityKF8NH




[svn:perl6-synopsis] r14564 - doc/trunk/design/syn

2008-07-16 Thread larry
Author: larry
Date: Wed Jul 16 15:53:34 2008
New Revision: 14564

Modified:
   doc/trunk/design/syn/S04.pod

Log:
typo from Brandon++


Modified: doc/trunk/design/syn/S04.pod
==
--- doc/trunk/design/syn/S04.pod(original)
+++ doc/trunk/design/syn/S04.podWed Jul 16 15:53:34 2008
@@ -1290,7 +1290,7 @@
 do not need a compile-time C::= binding, but like global subs,
 they perform a C:= binding to the lexical symbol at clone time
 (again, conceptually at the entry to the outer lexical scope, but
-possible deferred.)
+possibly deferred.)
 
 sub foo {
# conceptual cloning happens to both blocks below


Re: Complex planes

2008-07-16 Thread Jon Lang
Mark Biggar wrote:
 Let's worry about getting principal values, branch cuts and handling signed 
 zeros correct before dealing with the interaction of junctions and 
 multi-valued complex functions.

Indeed.

 BTW, two good references on this that we might want to plagiarizer.I mean 
 borrow from are the Ada Refernece Manual and the Common LISP Reference 
 Manual.  Both go into great detail on this subject.

I've just reviewed the Ada Reference Manual's take on this topic, and
it did indeed address a few wrinkles that I overlooked.

Basic rule: Complex.modulus = 0; Complex.arg ~~ -pi .. pi.

I'm not fully up on the lingo; so I'm going to invent some:  Number $x
is 'indefinite' if it is defined but has a value of Inf, NaN, or the
like.  It is 'definite' if it is defined and not indefinite.

If either .re or .im is indefinite, the complex number is indefinite.

If signed zeroes are used, then a definite complex number can always
be assigned to one of the four quadrants.  (In particular, if .im ==
-0, the number falls in one of the lower quadrants, and .arg == -pi or
-0, depending on whether .re is negative or positive, respectively; if
.im == +0, the number falls in one of the upper quadrants, and .arg ==
pi or +0.  It is impossible for .arg to be indefinite if both .re and
.im are definite: complex zeroes are signed by a definite .arg.)
Conjecture: signed zeroes should be accompanied by signed infinities:
as with zeroes, the sign of a complex infinity is a definite
argument.

Without signed zeroes, a definite complex number can be assigned to
one of the four quadrants, to the positive or negative real number
axes, to the positive or negative imaginary number axes, or to the
origin.  Under this scheme, some modifications and caveats need to be
stated: .arg ~~ -pi ^.. pi.  (So if the number falls on the negative
real number line, .arg == pi.) If the number is zero, .arg is
indefinite.  If the number is indefinite, .arg is indefinite.  If .re
is indefinite, then .im is indefinite, and vice versa.

The first paradigm has fewer special cases than the second one, but
has several redundancies of the same nature as signed zeroes; the
second paradigm more closely reflects what a mathematician would
expect when seeing a complex number, but has several incongruities
that might give a programmer headaches.

-- 
Jonathan Dataweaver Lang


Re: Complex planes

2008-07-16 Thread Brandon S. Allbery KF8NH


On 2008 Jul 16, at 18:48, Jon Lang wrote:


Moritz Lenz wrote:

Principle of least surprise:

Suppose sqrt(1) returns any(1, -1):
if sqrt($x)  0.5 { do something }

I can see the big, fat WTF written in the face of programmer who  
tries
to debug that code, and doesn't know about junctions. It just won't  
DTRT.


This is closely related to my original point.  In particular, if
you're unwilling to have sqrt return junctions of distinct values, you
don't really want to mess with junctions of a single complex value on
different planes, either.


I suggest that the base library not bother with any of this; if  
someone wants it they can load a FullComplex module or something like  
that.


--
brandon s. allbery [solaris,freebsd,perl,pugs,haskell] [EMAIL PROTECTED]
system administrator [openafs,heimdal,too many hats] [EMAIL PROTECTED]
electrical and computer engineering, carnegie mellon universityKF8NH