Roger's approach also fails if the numbers are big enough. Here's the
original problem, but with the last number changed to protect the innocent
(and make the demonstration work)
(4 : '13|x*y') / 19 29 59 79 89 109 119 139 149 179 198
3
Now let's use some big numbers:
(4 : '13|x*y') / 19 29 59 79 89 109 119 139 149 179 198 + 10^20
0
But if we use extended precision:
(4 : '13|x*y') / 19 29 59 79 89 109 119 139 149 179 198 + 10x^20
1
Showing interim results:
(4 : '13|x*y') /\. 19 29 59 79 89 109 119 139 149 179 198 + 10x^20
1 7 6 2 8 3 3 5 1 7 100000000000000000198
For that matter, my original approach will work with the same big numbers
as long as you use extended precision:
13|*/13|/ 19 29 59 79 89 109 119 139 149 179 198 + 10x^20
1
However, 0 can be a valid result in these remainder problems. Notice the
changed last digit (195 is a multiple of 13):
(4 : '13|x*y') / 19 29 59 79 89 109 119 139 149 179 195
0
(4 : '13|x*y') /\. 19 29 59 79 89 109 119 139 149 179 195
0 0 0 0 0 0 0 0 0 0 195
Any number in the list which is a multiple of 13, will cause the final
answer to be zero.
So you can't rely on a zero answer to indicate a "precision exceeded"
error. Which is why it would be nice to have a way to be notified when you
are exceeding the precision limit.
Skip
Skip Cave
Cave Consulting LLC
On Mon, Sep 18, 2017 at 3:48 PM, Skip Cave <[email protected]> wrote:
> So does Roger's function work on the larger list? Let's see:
>
> (4 : '13|x*y') / 10 # 19 29 59 79 89 109 119 139 149 179 199
>
> 9
>
> That looks like it does. Let's check with extended precision:
>
> (4 : '13|x*y') / 10 # 19 29 59 79 89 109 119 139 149 179 199x
>
> 9
>
> So Roger's approach works without extended precision. But mine doesn't:
>
>
> 13| */13|/ 10 # 19 29 59 79 89 109 119 139 149 179 199
>
> 0
>
> Let's see why. Here's Roger's verb. We'll call it 'g':
>
> g=. 4 : '13|x*y'
>
> Roger does g/ which puts g between each integer. Let's see what is going
> on In the short case:
>
> 19 g 29 g 59 g 79 g 89 g 109 g 119 g 139 g 149 g 179 g 199
>
> 4
>
>
> Step-by-step...
>
>
> 179 g 199
>
> 1
>
> 149 g 1
>
> 6
>
> 139 g 6
>
> 2
>
> 119 g 2
>
> 4
>
> 109 g 4
>
> 7
>
> 89 g 7
>
> 12
>
> 79 g 12
>
> 12
>
> 59 g 12
>
> 6
>
> 29 g 6
>
> 5
>
> 19 g 5
>
> 4
>
> So the secret is that Roger's scheme keeps the interim calculation values
> small enough to avoid precision errors. (There's got to be an easier way to
> list the interim values of insert). My scheme generated large interim
> values which exceeded the precision limit.
>
> Skip
>
>
> I get a set of numbers from a database. The
>
> Skip Cave
> Cave Consulting LLC
>
> On Mon, Sep 18, 2017 at 2:51 PM, Skip Cave <[email protected]>
> wrote:
>
>> Roger said:
>>
>> But if the list were longer:
>> 13 | */ 13 | 10 # 19 29 59 79 89 109 119 139 149 179 199
>> 0
>>
>> Wow! Yes I see the problem. It would be really nice if J would output a
>> warning when a calculation exceeds the precision limits. I'm sure this
>> would probably slow down all computations, so having a global variable to
>> turn on precision errors would be a conservative approach.
>>
>> Of course, I can usually check to see if an error has occurred by turning
>> on extended precision to see if the answers match, but it would be nice to
>> know without having to always double check my calculations..
>>
>> 13|*/13|/ 10 # 19 29 59 79 89 109 119 139 149 179 199x
>>
>> 9
>>
>>
>> Skip Cave
>> Cave Consulting LLC
>>
>> On Mon, Sep 18, 2017 at 1:46 PM, Roger Hui <[email protected]>
>> wrote:
>>
>>> Your solution works only because the list isn't too long, and the initial
>>> 13| (same as 13 |/) made them all small enough that you can do the */
>>> without losing precision. But if the list were longer:
>>>
>>> 13 | */ 13 | 10 # 19 29 59 79 89 109 119 139 149 179 199
>>> 0
>>>
>>> If it makes it more understandable, use explicit defn:
>>>
>>> (4 : '13|x*y') / 19 29 59 79 89 109 119 139 149 179 199
>>> 4
>>>
>>> "Multiplication mod m" means m|x*y, multiply, then take the remainder of
>>> division by m.
>>>
>>>
>>>
>>>
----------------------------------------------------------------------
For information about J forums see http://www.jsoftware.com/forums.htm