Bug?

20 views
Skip to first unread message

Ralf Hemmecke

unread,
Jan 29, 2019, 4:26:13 PM1/29/19
to fricas-devel
Can someone confirm the following problem?

Ralf

(1) -> f:=factor(x^2-1)

(1) (x - 1)(x + 1)
Type:
Factored(Polynomial(Integer))
(2) -> g:=f*(x-1)

2
(2) (x - 1) (x + 1)
Type:
Factored(Polynomial(Integer))
(3) -> h := g+1

>> Error detected within library code:
"failed" of mode Union(Factored(Polynomial(Integer)),"failed") cannot
be coerced to mode Factored(Polynomial(Integer))

oldk1331

unread,
Jan 29, 2019, 8:36:46 PM1/29/19
to fricas...@googlegroups.com
Yes, this is a bug introduced during my cleanup of Factored domain.

The fix is simple (I've commit it; see below).

The original thought is to avoid extra allocation of "0" and "1",
by reusing the argument:

zero? u => u
zero? v => v

but I wrote "zero? u or zero? v => u".

Now to think about it, if we really want to avoid extra allocation,
a better approach is to use local variable:

__one := [1, empty()]
1 == __one

====================================
--- src/algebra/fr.spad (revision 2550)
+++ src/algebra/fr.spad (working copy)
@@ -266,7 +266,7 @@
_*/[convert(f.factor)@DoubleFloat ^ f.exponent for f in
factorList x]

u : % * v : % ==
- zero? u or zero? v => u
+ zero? u or zero? v => 0
one? u => v
one? v => u
lu := factorList u; lv := factorList v
@@ -425,7 +425,7 @@
(expand((u exquo u1)::%) + expand((v exquo u1)::%)) * u1

gcd(u, v) ==
- one? u or one? v => u
+ one? u or one? v => 1
zero? u => v
zero? v => u
lu := factorList u; lv := factorList v

Ralf Hemmecke

unread,
Jan 30, 2019, 4:14:00 AM1/30/19
to fricas...@googlegroups.com
On 1/30/19 2:36 AM, oldk1331 wrote:
> Yes, this is a bug introduced during my cleanup of Factored domain.

Thanks for fixing it so quickly.

> Now to think about it, if we really want to avoid extra allocation,
> a better approach is to use local variable:
>
> __one := [1, empty()]
> 1 == __one

Honestly, it would surprise me if that works. In fact, I believe in
Aldor that would even lead to a subtle bug. The Aldor compiler reorders
== and := assignments. == assignments always come first. Maybe Peter
Broadbery can say more about it.

Have you checked whether in FriCAS

1 == [1, empty()]

i.e., the current situation, really leads to allocation of a new record
each time 1 is used?

In fact, it keeps confusing me.

In Aldor, if write something like

foo: % == [1, empty()]
bar(): % == [1, empty()]

then in the use of bar() I would expect a new allocation every time
bar() is used. But not so for foo. In Aldor bar is a function but foo is
a constant (no function call).

I were happy it that would be the same in FriCAS, but 1 in FriCAS is
ONE() and not really a constant. :-(

Ralf

oldk1331

unread,
Jan 30, 2019, 5:58:27 AM1/30/19
to fricas...@googlegroups.com
On 1/30/19 5:13 PM, Ralf Hemmecke wrote:
> On 1/30/19 2:36 AM, oldk1331 wrote:
>> Yes, this is a bug introduced during my cleanup of Factored domain.
>
> Thanks for fixing it so quickly.
>
>> Now to think about it, if we really want to avoid extra allocation,
>> a better approach is to use local variable:
>>
>> __one := [1, empty()]
>> 1 == __one
>
> Honestly, it would surprise me if that works. In fact, I believe in
> Aldor that would even lead to a subtle bug. The Aldor compiler reorders
> == and := assignments. == assignments always come first. Maybe Peter
> Broadbery can say more about it.
>
> Have you checked whether in FriCAS
>
> 1 == [1, empty()]
>
> i.e., the current situation, really leads to allocation of a new record
> each time 1 is used?

Hmm, I checked, I was wrong. Each usage of "1" doesn't leads to a new
allocation.

> In fact, it keeps confusing me.
>
> In Aldor, if write something like
>
> foo: % == [1, empty()]
> bar(): % == [1, empty()]
>
> then in the use of bar() I would expect a new allocation every time
> bar() is used. But not so for foo. In Aldor bar is a function but foo is
> a constant (no function call).

I think "foo" and "bar" are the same: the empty parentheses can be omitted.
They are both functions with no arguments.

The thing matters is that "1" is declared as:

1 : constant -> %

That makes sure function body of "1" is called only once.

So in

foo1 : () -> %
foo2 : constant -> %

the function body of "foo1" will run many times and the function body of "foo2"
will run only once. I didn't know this distinction before...

Bill Page

unread,
Jan 30, 2019, 12:46:24 PM1/30/19
to fricas-devel
On Wed, Jan 30, 2019 at 5:58 AM oldk1331 <oldk...@gmail.com> wrote:
>
> On 1/30/19 5:13 PM, Ralf Hemmecke wrote:
> ...
> > In fact, it keeps confusing me.
> >
> > In Aldor, if write something like
> >
> > foo: % == [1, empty()]
> > bar(): % == [1, empty()]
> >
> > then in the use of bar() I would expect a new allocation every time
> > bar() is used. But not so for foo. In Aldor bar is a function but foo is
> > a constant (no function call).
>
> I think "foo" and "bar" are the same: the empty parentheses can be omitted.
> They are both functions with no arguments.
>
> The thing matters is that "1" is declared as:
>
> 1 : constant -> %
>
> That makes sure function body of "1" is called only once.
>
> So in
>
> foo1 : () -> %
> foo2 : constant -> %
>
> the function body of "foo1" will run many times and the function body of "foo2"
> will run only once. I didn't know this distinction before...
>

Thank you! I think this distinction is clear and important.
Reply all
Reply to author
Forward
0 new messages