bug-apl
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Bug-apl] Modulo or residue function is not generating consistent co


From: Juergen Sauermann
Subject: Re: [Bug-apl] Modulo or residue function is not generating consistent complete residue systems for some arguments
Date: Sat, 24 Jun 2017 18:46:04 +0200
User-agent: Mozilla/5.0 (X11; Linux i686; rv:45.0) Gecko/20100101 Thunderbird/45.2.0

Hi Fred,

OK, I was using 
4J¯1 because that was the number where I believed you
were suspocting the error/difference was. But OK, 5J3 | 4J¯1 is ¯4J1
on your box and on mine.

Now to 5J3 | ¯7J6:

My machine says:
 
      5J3 | ¯7J6
⎕CT is: 1e-13
modulus (A) is: (5,3)
A=0 is: (0,0)
A+A=0 is: (5,3)
B÷A+A=0 is: (-0.5,1.5)
⌊B÷A+A=0 is: (0,1)
A×⌊B÷A+A=0 is: (-3,5)
B-A×⌊B÷A+A=0 is: (-4,1)
¯4J1


Both machines agree that:

B÷A+A=0 is: (-0.5,1.5)

but they disagree what
-0.5,1.5 should be. My machine says 0J1
while yours says ¯1J2. That is, my machine rounds down the real part and rounds
up the imag part, while yours rounds up the real part and rounds down the
imag part.

SInce the code of bif_floor() has become quite trivial recently:

ErrorCode
ComplexCell::bif_floor(Cell * Z) const
{
const APL_Float fr = floor(value.cval_r);    // fr ≤ value.cval_r
const APL_Float Dr = value.cval_r - fr;      // 0 ≤ Dr < 1
const APL_Float fi = floor(value2.cval_i);   // fi ≤ value2.cval_i
const APL_Float Di = value2.cval_i - fi;     // 0 ≤ Di < 1
const APL_Float D = Dr + Di;                 // 0 ≤ D < 2

   if (D < 1.0 - Workspace::get_CT())   return zv(Z, fr, fi);   // ISO

   if (Dr < Di)   return zv(Z, fr, fi + 1.0);
   else           return zv(Z, fr + 1.0, fi);
}


it appears as if our machines disagree on the comparison
Dr < Di. The Dr (for difference real) and Di (for difference
imag) are exactly the x and y in the McDonnell paper. So your machine lands in area c while mine lands in area b of
Figure 2 in the paper.

That explains what we see, but not what we can do about it.

The ISO standard (which interestingly lists McDonnell as one of the 3 editors) computes Dr + Di < 1 as a tolerant compare
(i.e. involves ⎕CT in the test for equality (page 19 of the ISO standard)) and computes
Dr < Di as a strict compare (i.e.
not considering ⎕CT). The APL2 language reference claims that both comparisons are made with ⎕CT=0. It
might be that both are wrong.

My proposal would therefore be to change the last if statement like this:


   if (Dr < Di
- Workspace::get_CT())   return zv(Z, fr, fi + 1.0);

Maybe you want to try that with the last debug version of ComplexCell.cc that I sent earlier today
before I commit it as a new SVN version.

Best Regards,
Jürgen Sauermann


On 06/24/2017 04:54 PM, Frederick Pitts wrote:
Jürgen,

A cut-and-paste of the output on my platform is:

      5J3 | 4J¯1
⎕CT is: 1e-13
modulus (A) is: (5,3)
A=0 is: (0,0)
A+A=0 is: (5,3)
B÷A+A=0 is: (0.5,-0.5)
⌊B÷A+A=0 is: (1,-1)
A×⌊B÷A+A=0 is: (8,-2)
B-A×⌊B÷A+A=0 is: (-4,1)
¯4J1

It is identical to the output you supplied me. But I don't think an error occurs during the evaluation of 5J3 | 4J¯1. I think
the error occurs during the evaluation of

      5J3 | ¯7J6
⎕CT is: 1e-13
modulus (A) is: (5,3)
A=0 is: (0,0)
A+A=0 is: (5,3)
B÷A+A=0 is: (-0.5,1.5)
⌊B÷A+A=0 is: (-1,2)
A×⌊B÷A+A=0 is: (-11,7)
B-A×⌊B÷A+A=0 is: (4,-1)
4J¯1

because it says 4J¯1 is in the complete residue system for modulus 5J3, while the 5J3 | 4J¯1 evaluation above says it isn't.
If it were, evaluating 5J3 | 4J¯1 should spit 4J¯1 back at me.

Here is a transcript of evaluating 5J3 | ¯7J6 using the McDonnell floor function I sent in an
earlier email

      A ← 5J3
      A = 0
0
      A + A = 0
5J3
      B ← ¯7J6
      B ÷ A + A = 0
¯0.5J1.5
      floor B ÷ A + A = 0
0J1
      A × floor B ÷ A + A = 0
¯3J5
      B - A × floor B ÷ A + A = 0
¯4J1

Note that the result of the floor evaluation is 0J1, not ¯1J2 and that residue result at the end is correct.

Regards,

Fred




reply via email to

[Prev in Thread] Current Thread [Next in Thread]