holonomic functions

1 view
Skip to first unread message

Martin Rubey

unread,
Jan 26, 2009, 4:07:17 AM1/26/09
to fricas-devel
Now that LODO works, below a *very* rudimentary version of a holonomic function
domain.

Missing, roughly in order of importance

* zero test

* hadamard product, algebraic substitution, integration, differentiation

* a recurrence version (should be trivial), along with appropriate coercions

* q-versions (should be trivial)

* sensible domain parameters

* a creation operation, i.e., given a linear homogeneous diffeq and initial
values, create a holonomic function

* RetractableTo EXPR INT, i.e., a solver that goes together with the creation
operation. I think it's best to have the Rep include also an EXPR INT.

* "normalization" of the diffeq: we should have one domain where this is done
automatically, another one where it's done on request only

moreover:

* generalisation to ADE's

* a domain for algebraic functions, so that UHOLO has
Eltable(AlgebraicFunction, %)

* generalisation to the multivariate case

Martin

\documentclass{article}
\usepackage{axiom,amsthm,amsmath,url}
\newtheorem{ToDo}{ToDo}[section]

\newcommand{\Axiom}{{\tt Axiom}}
\newcommand{\Rate}{{\tt Rate}}
\newcommand{\GFUN}{{\tt GFUN}}
\begin{document}
\title{holonomic.spad}
\author{Martin Rubey}
\maketitle
\begin{abstract}
\end{abstract}
\tableofcontents
\section{domain UHOLO1 UnivariateHolonomicSeries1}
<<domain UHOLO1 UnivariateHolonomicSeries1>>=
)abbrev domain UHOLO1 UnivariateHolonomicSeries1
UnivariateHolonomicSeries1(Coef: Join(Field, DifferentialRing)):
Exports == Implementation where

UFPS ==> UnivariateFormalPowerSeries Coef
DEQCOEF ==> SparseUnivariatePolynomial Coef
FDEQCOEF ==> Fraction DEQCOEF
LODO1 ==> LinearOrdinaryDifferentialOperator1 FDEQCOEF

Exports ==> AbelianMonoidRing(Coef, NonNegativeInteger) with

sin: () -> %
cos: () -> %
atan: () -> %
exp: () -> %

series: % -> UFPS
differentialEquation: % -> LODO1

Implementation ==> add
Rep := Record(eq : LODO1, init: UFPS)

series f == f.init

differentialEquation f == f.eq

coerce(f: %): OutputForm ==
bracket([f.eq::OutputForm,
f.init::OutputForm])$OutputForm

-- x*Dx x^n = x*n*x^(n-1)=n*x^n

Dx := D()$LODO1
monomial(c, n) ==
c1: FDEQCOEF := monomial(1,1)$DEQCOEF :: FDEQCOEF
c0: FDEQCOEF := (-n)::DEQCOEF :: FDEQCOEF
[c1*Dx+c0*1$LODO1, monomial(c,n)]$Rep
0 == [1, 0]$Rep
1 == [Dx, 1]$Rep
f + g == [directSum(f.eq, g.eq), f.init + g.init]
(n: Integer) * (f: %) == [f.eq, n*f.init]
(f: %) * (g: %) == [symmetricProduct(f.eq, g.eq), f.init * g.init]$Rep
sin() == [Dx**2+1, sin(monomial(1,1)$UFPS)$UFPS]$Rep
cos() == [Dx**2+1, cos(monomial(1,1)$UFPS)$UFPS]$Rep
exp() == [Dx-1, exp(monomial(1,1)$UFPS)$UFPS]$Rep
atan() ==
c2: FDEQCOEF := (monomial(1,2)$DEQCOEF+1)::FDEQCOEF
c1: FDEQCOEF := monomial(2*1$Coef,1)$DEQCOEF::FDEQCOEF
[c2*Dx**2+c1*Dx, atan(monomial(1,1)$UFPS)$UFPS]$Rep

@
%$

<<*>>=
<<domain UHOLO1 UnivariateHolonomicSeries1>>
@
\end{document}

Martin Rubey

unread,
Jan 26, 2009, 1:49:40 PM1/26/09
to fricas...@googlegroups.com
Martin Rubey <martin...@math.uni-hannover.de> writes:

I now implemented also integration and differentiation, and noticed something I
don't really like:

(1) -> Dx:=D()$LODO1(FRAC UP(x, INT))

(1) D
Type: LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))
(2) -> Dx*x

(2) x D
Type: LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))
(3) -> Dx*(x::LODO1 FRAC UP(x, INT))

(3) x D + 1
Type: LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))

I think that (2) and (3) should give the same result, namely x D + 1. I do not
see a reason to have right multiplication by an element of the coefficient ring
differ from multiplication of operators.

Martin

\documentclass{article}
\usepackage{axiom,amsthm,amsmath,url}
\newtheorem{ToDo}{ToDo}[section]

\newcommand{\Axiom}{{\tt Axiom}}
\newcommand{\Rate}{{\tt Rate}}
\newcommand{\GFUN}{{\tt GFUN}}
\begin{document}
\title{holonomic.spad}
\author{Martin Rubey}
\maketitle
\begin{abstract}
\end{abstract}
\tableofcontents
\section{domain UHOLO1 UnivariateHolonomicSeries1}

<<domain UALG UnivariateAlgebraicSeries>>=
)abbrev domain UALG UnivariateAlgebraicSeries
UnivariateAlgebraicSeries(Coef: Algebra Fraction Integer):
Exports == Implementation where

@

\section{domain UHOLO1 UnivariateHolonomicSeries1}
<<domain UHOLO1 UnivariateHolonomicSeries1>>=
)abbrev domain UHOLO1 UnivariateHolonomicSeries1

UnivariateHolonomicSeries1(Coef: Algebra Fraction Integer):
Exports == Implementation where

UFPS ==> UnivariateFormalPowerSeries Coef
DEQCOEF ==> UnivariatePolynomial(x, Coef)


FDEQCOEF ==> Fraction DEQCOEF
LODO1 ==> LinearOrdinaryDifferentialOperator1 FDEQCOEF

Exports ==> Join(AbelianMonoidRing(Coef, NonNegativeInteger),
DifferentialRing) with

sin: () -> %
cos: () -> %
atan: () -> %
exp: () -> %

integrate: % -> %

series: % -> UFPS
differentialEquation: % -> LODO1

Implementation ==> add
Rep := Record(eq : LODO1, init: UFPS)

series f == f.init

differentialEquation f == f.eq

coerce(f: %): OutputForm ==
bracket([f.eq::OutputForm,
f.init::OutputForm])$OutputForm

Dx := D()$LODO1

0 == [1, 0]$Rep
1 == [Dx, 1]$Rep

-- x*Dx x^n = x*n*x^(n-1)=n*x^n


monomial(c, n) ==
c1: FDEQCOEF := monomial(1,1)$DEQCOEF :: FDEQCOEF
c0: FDEQCOEF := (-n)::DEQCOEF :: FDEQCOEF
[c1*Dx+c0*1$LODO1, monomial(c,n)]$Rep

f + g == [directSum(f.eq, g.eq), f.init + g.init]

(n: Integer) * (f: %) == [f.eq, n*f.init]
(f: %) * (g: %) == [symmetricProduct(f.eq, g.eq), f.init * g.init]$Rep

integrate f == [f.eq*Dx, integrate f.init]

D f ==
p0 := coefficient(f.eq, 0)
Deq: LODO1
if zero? p0
then Deq := f.eq
else
-- without the parenthesis below, we would use ordinary multiplication!
Deq := Dx * (inv p0 * f.eq)

lmo: List LODO1
:= [monomial(coefficient(Deq, i+1), i)$LODO1 _
for i in 0..degree Deq - 1]

[reduce(_+$LODO1, lmo, 0), D f.init]

Ralf Hemmecke

unread,
Jan 26, 2009, 6:16:21 PM1/26/09
to fricas...@googlegroups.com
On 01/26/2009 07:49 PM, Martin Rubey wrote:
> I now implemented also integration and differentiation, and noticed something I
> don't really like:
>
> (1) -> Dx:=D()$LODO1(FRAC UP(x, INT))
>
> (1) D
> Type: LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))
> (2) -> Dx*x
>
> (2) x D
> Type: LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))
> (3) -> Dx*(x::LODO1 FRAC UP(x, INT))
>
> (3) x D + 1
> Type: LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))

> I think that (2) and (3) should give the same result, namely x D + 1. I do not
> see a reason to have right multiplication by an element of the coefficient ring
> differ from multiplication of operators.

Of course, the computer is right. ;-) But I agree, that is not really
what one wants in that situation. I'd rather like to see the coercion

x::LODO1 FRAC UP(x, INT)

happen automatically or the right multiplication with a coefficient done
correctly.

The reason for (2) and (3) not being equal lies in the definition of
LinearOrdinaryDifferentialOperator1. Its category is
LinearOrdinaryDifferentialOperatorCategory(A) and that inherits from
UnivariateSkewPolynomialCategory A. But if you look into its source in
ore.spad, you'll find:

UnivariateSkewPolynomialCategory(R:Ring):
Category == Join(Ring, BiModule(R, R), FullyRetractableTo R) with
^^^^^^^^^^^^^^

That, by itself, would not be the problem. It is only a problem if the
right multiplication by a coefficient is not implemented according to
the commutation rules.

What I found is that

LinearOrdinaryDifferentialOperator(A:Ring, diff: A -> A):
LinearOrdinaryDifferentialOperatorCategory A
== SparseUnivariateSkewPolynomial(A, 1, diff) add ...

and

SparseUnivariateSkewPolynomial(R:Ring, sigma:Automorphism R, delta: R -> R):
UnivariateSkewPolynomialCategory R with
outputForm: (%, OutputForm) -> OutputForm
== SparseUnivariatePolynomial R add

And the last line is the problem. It certainly implements multiplication
from the right, but, of course, in a commutative fashion.

Multiplication from the right should rather expand the definition

x * a == \sigma(a) * x + \delta(a)

where x is the indeterminate of the skewpolynomial ring.

So, I guess, adding

(z: %) * (r: R): % == times(z, r*(1$%), sigma, delta)

into the second chunk

<<domain ORESUP SparseUnivariateSkewPolynomial>>=

should solve Martin's problem and all the others that are just connected
to skew polynomials.

Other opinions?


BTW... it is *totally* ugly that this chunk

<<domain ORESUP SparseUnivariateSkewPolynomial>>

is split in two in such a way as it currently is.
I'd rather like to see something like

<<domain ORESUP SparseUnivariateSkewPolynomial>>=
)abbrev domain ORESUP SparseUnivariateSkewPolynomial
...
SparseUnivariateSkewPolynomial(R:Ring,sigma:Automorphism R,delta:R->R):
UnivariateSkewPolynomialCategory R with
...
== SparseUnivariatePolynomial R add
<<domain ORESUP SparseUnivariateSkewPolynomial: add-body>>
@


<<domain ORESUP SparseUnivariateSkewPolynomial: add-body>>=
import RepeatedSquaring(%)
_^(x:%, n:PositiveInteger):% == x ** n
...
if R has Field then
leftDivide(a, b) == leftDivide(a, b, sigma)
rightDivide(a, b) == rightDivide(a, b, sigma)
@

Common initial white space should not be important in a chunk.

Best regards
Ralf

Martin Rubey

unread,
Jan 26, 2009, 6:27:03 PM1/26/09
to fricas...@googlegroups.com
next version...

I don't particularly like the design, improvements welcome. Documentation
non-existing currently, too.

Usage example:

(33) -> cat2 := coerce(univariate(x::UP(x, FRAC INT)*y^2-y+1,y)::SUP UP(x, FRAC INT), 0)$UALG FRAC INT

2
(33) [x ? - ? + 1,0]
Type: UnivariateAlgebraicSeries(Fraction(Integer))
Time: 0.14 (IN) + 0.004 (EV) + 0.05 (OT) = 0.19 sec
(34) -> cat2 * cat2

3 3 2 2
(34) [x ? + (x - x)? + (- x + 1)? - 1,0]
Type: UnivariateAlgebraicSeries(Fraction(Integer))
Time: 0.01 (EV) + 0.02 (OT) = 0.03 sec

check:
(71) -> cs := series([1/(2*n+1)*binomial(2*n+1, n) for n in 0..])$UFPS FRAC INT

(71)
2 3 4 5 6 7 8 9
1 + x + 2x + 5x + 14x + 42x + 132x + 429x + 1430x + 4862x
+
10 11
16796x + O(x )
Type: UnivariateFormalPowerSeries(Fraction(Integer))
Time: 0.02 (IN) + 0.03 (OT) = 0.05 sec
(72) -> guessAlg(entries complete first(coefficients(cs2*cs2), 42),
maxPower==6)

(72)
[
[
function =
n 2 2
[[x ]f(x): x f(x) + (2x - 1)f(x) + 1= 0,
2 3 4 5
f(x)= 1 + 2x + 5x + 14x + 42x + O(x )]
,
order= 0]
]
Type: List(Record(function: Expression(Integer),order: NonNegativeInteger))
Time: 0.08 (EV) + 0.01 (OT) = 0.08 sec
Martin

\documentclass{article}
\usepackage{axiom,amsthm,amsmath,url}
\newtheorem{ToDo}{ToDo}[section]

\newcommand{\Axiom}{{\tt Axiom}}
\newcommand{\Rate}{{\tt Rate}}
\newcommand{\GFUN}{{\tt GFUN}}
\begin{document}
\title{holonomic.spad}
\author{Martin Rubey}
\maketitle
\begin{abstract}
\end{abstract}
\tableofcontents

\section{domain UALG UnivariateAlgebraicSeries}


<<domain UALG UnivariateAlgebraicSeries>>=
)abbrev domain UALG UnivariateAlgebraicSeries
UnivariateAlgebraicSeries(Coef: Algebra Fraction Integer):
Exports == Implementation where

UFPS ==> UnivariateFormalPowerSeries Coef
EQCOEF ==> UnivariatePolynomial(x, Coef)
ALGEQ ==> SparseUnivariatePolynomial EQCOEF

Exports ==> Join(AbelianMonoidRing(Coef, NonNegativeInteger),
DifferentialRing, Field) with

coerce: (ALGEQ, UFPS) -> %

Implementation ==> add
Rep := Record(eq: ALGEQ, init: UFPS)

coerce(f: %): OutputForm ==
bracket([f.eq::OutputForm,
f.init::OutputForm])$OutputForm

coerce(feq: ALGEQ, finit: UFPS): % == [feq, finit]$Rep

0 == [monomial(1,1)$ALGEQ, 0]$Rep
1 == [monomial(1,1)$ALGEQ-1, 1]$Rep

monomial(c, n) ==
[monomial(1,1)$ALGEQ-monomial(c,n)$EQCOEF::ALGEQ,
monomial(c,n)]$Rep

FEQCOEF ==> Fraction EQCOEF
OVAR ==> OrderedVariableList ['u, 'v, 'y]
SMP ==> SparseMultivariatePolynomial(FEQCOEF, OVAR)
GROE ==> GroebnerPackage(FEQCOEF, IndexedExponents OVAR, OVAR, SMP)
CDEN ==> CommonDenominator(EQCOEF,FEQCOEF,List FEQCOEF)
SUP2EF ==> SparseUnivariatePolynomialFunctions2(EQCOEF, FEQCOEF)
SUP2FE ==> SparseUnivariatePolynomialFunctions2(FEQCOEF, EQCOEF)

f + g ==
ff: SparseUnivariatePolynomial FEQCOEF
:= map(#1::FEQCOEF, f.eq)$SUP2EF
gf: SparseUnivariatePolynomial FEQCOEF
:= map(#1::FEQCOEF, g.eq)$SUP2EF
leq: List SMP :=
[index(3)$OVAR::SMP-index(1)$OVAR::SMP-index(2)$OVAR::SMP, _
multivariate(ff, index(1)$OVAR), _
multivariate(gf, index(2)$OVAR)]
neweq: SMP := third groebner(leq)$GROE
neweq2: SparseUnivariatePolynomial FEQCOEF := univariate(neweq)$SMP
cden: EQCOEF := commonDenominator(coefficients neweq2)$CDEN

algeq: ALGEQ := map(retract(cden*#1)@EQCOEF, neweq2)$SUP2FE
[algeq, f.init + g.init]$Rep

(f: %) * (g: %) ==

ff: SparseUnivariatePolynomial FEQCOEF
:= map(#1::FEQCOEF, f.eq)$SUP2EF
gf: SparseUnivariatePolynomial FEQCOEF
:= map(#1::FEQCOEF, g.eq)$SUP2EF
leq: List SMP :=
[index(3)$OVAR::SMP-index(1)$OVAR::SMP*index(2)$OVAR::SMP, _
multivariate(ff, index(1)$OVAR), _
multivariate(gf, index(2)$OVAR)]
gb := groebner(leq)$GROE
output(gb::OutputForm)$OutputPackage
neweq: SMP := last gb
output(variables(neweq)$SMP::OutputForm)$OutputPackage
neweq2: SparseUnivariatePolynomial FEQCOEF := univariate(neweq)$SMP
cden: EQCOEF := commonDenominator(coefficients neweq2)$CDEN

algeq: ALGEQ := map(retract(cden*#1)@EQCOEF, neweq2)$SUP2FE
[algeq, f.init * g.init]$Rep

@

integrate: % -> %

series f == f.init

differentialEquation f == f.eq

Dx := D()$LODO1

@
%$

<<*>>=
<<domain UALG UnivariateAlgebraicSeries>>

Martin Rubey

unread,
Jan 26, 2009, 6:29:21 PM1/26/09
to fricas...@googlegroups.com
Ralf Hemmecke <ra...@hemmecke.de> writes:

> SparseUnivariateSkewPolynomial(R:Ring, sigma:Automorphism R, delta: R -> R):
> UnivariateSkewPolynomialCategory R with
> outputForm: (%, OutputForm) -> OutputForm
> == SparseUnivariatePolynomial R add
>
> And the last line is the problem. It certainly implements multiplication
> from the right, but, of course, in a commutative fashion.

Yes.



> Multiplication from the right should rather expand the definition
>
> x * a == \sigma(a) * x + \delta(a)
>
> where x is the indeterminate of the skewpolynomial ring.
>
> So, I guess, adding
>
> (z: %) * (r: R): % == times(z, r*(1$%), sigma, delta)
>
> into the second chunk
>
> <<domain ORESUP SparseUnivariateSkewPolynomial>>=
>
> should solve Martin's problem and all the others that are just connected
> to skew polynomials.

I'm all for it.



> BTW... it is *totally* ugly that this chunk
>
> <<domain ORESUP SparseUnivariateSkewPolynomial>>
>
> is split in two in such a way as it currently is.
> I'd rather like to see something like
>
> <<domain ORESUP SparseUnivariateSkewPolynomial>>=
> )abbrev domain ORESUP SparseUnivariateSkewPolynomial
> ...
> SparseUnivariateSkewPolynomial(R:Ring,sigma:Automorphism R,delta:R->R):
> UnivariateSkewPolynomialCategory R with
> ...
> == SparseUnivariatePolynomial R add
> <<domain ORESUP SparseUnivariateSkewPolynomial: add-body>>
> @
>
>
> <<domain ORESUP SparseUnivariateSkewPolynomial: add-body>>=
> import RepeatedSquaring(%)
> _^(x:%, n:PositiveInteger):% == x ** n
> ...
> if R has Field then
> leftDivide(a, b) == leftDivide(a, b, sigma)
> rightDivide(a, b) == rightDivide(a, b, sigma)
> @
>
> Common initial white space should not be important in a chunk.

Einverstanden!

Martin

Ralf Hemmecke

unread,
Jan 27, 2009, 5:08:48 AM1/27/09
to fricas...@googlegroups.com
>> (z: %) * (r: R): % == times(z, r*(1$%), sigma, delta)

I know that would be proper Aldor, but is this proper SPAD?
Whether this really fixes the problem, I first have to investigate, of
course.

Ralf

Martin Rubey

unread,
Jan 27, 2009, 5:47:45 AM1/27/09
to fricas...@googlegroups.com
Ralf Hemmecke <ra...@hemmecke.de> writes:

> >> (z: %) * (r: R): % == times(z, r*(1$%), sigma, delta)
>
> I know that would be proper Aldor, but is this proper SPAD?

As far as I can see, yes.

Martin

> Whether this really fixes the problem, I first have to investigate, of
> course.

I'm quite sure it does. We fixed already exponentiation this way. My question
really was: does anybody want to have it as it is currently, but it seems that
this is not the case, so: go ahead!

Martin

hemmecke

unread,
Jan 28, 2009, 5:53:59 PM1/28/09
to FriCAS - computer algebra system
I hope nobody will ever fall into the same trap as me.

In http://groups.google.com/group/fricas-devel/msg/b2e1c329ad300ad1
I suggested to introduce a sub-chunk with name

<<domain ORESUP SparseUnivariateSkewPolynomial: add-body>>=

You should never start a chunk that matches the pattern given in
src/scripts/find-algebra-files, namely:

<<(domain|package|category) .*>>=

unless you really intend to use that chunk to introduce a new
constructor.

My suggestion from above breaks the build process, since "find-algebra-
files"
falsely recognizes that "...: add-body" chunk as a new domain.

You have been warned!

Ralf

Ralf Hemmecke

unread,
Jan 29, 2009, 2:48:53 AM1/29/09
to fricas...@googlegroups.com
Hello,

Martin, do you like that more...

GCL (GNU Common Lisp) 2.6.7 CLtL1 Oct 29 2006 02:32:45
Source License: LGPL(gcl,gmp), GPL(unexec,bfd,xgcl)
Binary License: GPL due to GPL'ed components: (XGCL READLINE BFD UNEXEC)
Modifications of this banner must retain notice of a compatible license
Dedicated to the memory of W. Schelter

Use (help) to get some basic information on how to use GCL.
Temporary directory for compiler files set to /tmp/hemmecke/
openServer result 0
FriCAS (AXIOM fork) Computer Algebra System
Version: FriCAS 2009-01-25
Timestamp: Wednesday January 28, 2009 at 23:40:51
-----------------------------------------------------------------------------
Issue )copyright to view copyright notices.
Issue )summary for a summary of useful system commands.
Issue )quit to leave FriCAS and return to shell.
-----------------------------------------------------------------------------

(1) ->


(1) -> Dx:=D()$LODO1(FRAC UP(x, INT))
(1) D
Type:
LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))
(2) -> Dx*x

(2) x D + 1


Type:
LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))
(3) -> Dx*(x::LODO1 FRAC UP(x, INT))
(3) x D + 1
Type:
LinearOrdinaryDifferentialOperator1(Fraction(UnivariatePolynomial(x,Integer)))

I basically modified ore.spad as I described in
http://groups.google.com/group/fricas-devel/msg/b2e1c329ad300ad1 .
Patch is below. Should I commit?

Ralf

diff -Naur ore.spad.pamphlet.old ore.spad.pamphlet > ore.patch


ore.patch

Martin Rubey

unread,
Jan 29, 2009, 5:53:45 AM1/29/09
to fricas...@googlegroups.com
Ralf Hemmecke <ra...@hemmecke.de> writes:

> Hello,
>
> Martin, do you like that more...

Much better. However (sorry...), we should check whether the line

== SparseUnivariatePolynomial R add

is a good idea. Yes, the Rep is the same, and a few operations are the same,
but many are different.

I guess, the best thing is to write a test for *every* operation...
> --- ore.spad.pamphlet.old 2009-01-29 08:41:14.000000000 +0100
> +++ ore.spad.pamphlet 2009-01-28 23:39:04.000000000 +0100
> @@ -506,6 +506,7 @@
> ++ outputForm(p, x) returns the output form of p using x for the
> ++ otherwise anonymous variable.
> == SparseUnivariatePolynomial R add
> + <<ORESUP SparseUnivariateSkewPolynomial: add-body>>
> @
>
> We have to define \spadfun{**} and \verb|^|, because otherwise they would be
> @@ -513,7 +514,7 @@
> \spadtype{SemiGroup} and \spadtype{Monoid} are overridden. There might be a
> faster definition, of course.
>
> -<<domain ORESUP SparseUnivariateSkewPolynomial>>=
> +<<ORESUP SparseUnivariateSkewPolynomial: add-body>>=
> import RepeatedSquaring(%)
> _^(x:%, n:PositiveInteger):% == x ** n
> x:% ** n:PositiveInteger == expt(x,n)
> @@ -525,6 +526,7 @@
> import UnivariateSkewPolynomialCategoryOps(R, %)
>
> x:% * y:% == times(x, y, sigma, delta)
> + x:% * r:R == times(x, r*1, sigma, delta)
> apply(p, c, r) == apply(p, c, r, sigma, delta)
>
> if R has IntegralDomain then

Ralf Hemmecke

unread,
Jan 29, 2009, 6:12:24 AM1/29/09
to fricas...@googlegroups.com
> However (sorry...), we should check whether the line
>
> == SparseUnivariatePolynomial R add
>
> is a good idea. Yes, the Rep is the same, and a few operations are the same,
> but many are different.

Good spot!!!

> I guess, the best thing is to write a test for *every* operation...

I completely agree. But now you have to teach me.

1) Where can I find a documentation of all your testsuite business?
2) Where is the testsuite machinery? How does it roughly work?
3) Where are the test files? (I don't see a "test" directory.)

Ralf

Martin Rubey

unread,
Jan 29, 2009, 7:30:58 AM1/29/09
to fricas...@googlegroups.com
Ralf Hemmecke <ra...@hemmecke.de> writes:

> > However (sorry...), we should check whether the line
> >
> > == SparseUnivariatePolynomial R add
> >
> > is a good idea. Yes, the Rep is the same, and a few operations are the same,
> > but many are different.
>
> Good spot!!!
>
> > I guess, the best thing is to write a test for *every* operation...
>
> I completely agree. But now you have to teach me.
>
> 1) Where can I find a documentation of all your testsuite business?

in src/algebra/unittest.spad.pamphlet

> 2) Where is the testsuite machinery? How does it roughly work?

2a: ditto. 2b: write a .input file that looks roughly like
src/input/elemnum.input.pamphlet

> 3) Where are the test files? (I don't see a "test" directory.)

see 2b.

actually, there is a tiny bit of disagreement between Waldek and myself on
where to put the tests. I'd like to have "categorical" tests (i.e., black box
tests that test every operation a category exports) in the spad.pamphlet, then
"paedagogic", "explanatory", i.e., system tests in a file in src/input, and
regression tests in src/input/bugs20??.input.

Waldek had good reasons not to put tests into category definitions, so for the
moment we put all tests into src/input...

1 000 000 thanks for your work!

Martin

Martin Rubey

unread,
Jan 29, 2009, 9:05:05 AM1/29/09
to fricas...@googlegroups.com
Ralf Hemmecke <ra...@hemmecke.de> writes:

> > However (sorry...), we should check whether the line
> >
> > == SparseUnivariatePolynomial R add
> >
> > is a good idea. Yes, the Rep is the same, and a few operations are the same,
> > but many are different.
>
> Good spot!!!

just noticed that OREUP does not have POLYCAT, so, I guess that

> > == SparseUnivariatePolynomial R add

is really out of place. However, please commit the change you made first, and
then dig further. History shows that this makes development proceed faster.

Martin

Waldek Hebisch

unread,
Jan 30, 2009, 6:19:06 PM1/30/09
to fricas...@googlegroups.com
Ralf Hemmecke wrote:
> I basically modified ore.spad as I described in
> http://groups.google.com/group/fricas-devel/msg/b2e1c329ad300ad1 .
> Patch is below. Should I commit?
>

Yes. We should replace:

== SparseUnivariatePolynomial R add

by
== add
Rep := SparseUnivariatePolynomial R

but I agree with Martin that we should commit the fix first.

--
Waldek Hebisch
heb...@math.uni.wroc.pl

Gabriel Dos Reis

unread,
Jan 30, 2009, 6:33:52 PM1/30/09
to fricas...@googlegroups.com
Waldek Hebisch <heb...@math.uni.wroc.pl> writes:

| Ralf Hemmecke wrote:
| > I basically modified ore.spad as I described in
| > http://groups.google.com/group/fricas-devel/msg/b2e1c329ad300ad1 .
| > Patch is below. Should I commit?
| >
|
| Yes. We should replace:
|
| == SparseUnivariatePolynomial R add
|
| by
| == add
| Rep := SparseUnivariatePolynomial R
|
| but I agree with Martin that we should commit the fix first.

I would think that the first form is clearer and superior to the
second in that it clearly separates addon from addins and make the
connection. But, I agree that without better support in the
language -- where it is clear that the addon is the representation --
one would be forced to explicitly define Rep.

[ FWIW OpenAxiom automtically recognizes the construct and makes the
addon the reprsentation type. ]

Waldek Hebisch

unread,
Jan 30, 2009, 7:02:51 PM1/30/09
to fricas...@googlegroups.com
Gabriel Dos Reis wrote:
>
> Waldek Hebisch <heb...@math.uni.wroc.pl> writes:
>
> | Ralf Hemmecke wrote:
> | > I basically modified ore.spad as I described in
> | > http://groups.google.com/group/fricas-devel/msg/b2e1c329ad300ad1 .
> | > Patch is below. Should I commit?
> | >
> |
> | Yes. We should replace:
> |
> | == SparseUnivariatePolynomial R add
> |
> | by
> | == add
> | Rep := SparseUnivariatePolynomial R
> |
> | but I agree with Martin that we should commit the fix first.
>
> I would think that the first form is clearer and superior to the
> second in that it clearly separates addon from addins and make the
> connection. But, I agree that without better support in the
> language -- where it is clear that the addon is the representation --
> one would be forced to explicitly define Rep.
>

The first form is superior _if appropriate_. However, skew
polynomials are really more general that commutative polynomials,
and operations typically must take this into account. So
inheritance does not look appropriate here (logically it would
be appropriate if SparseUnivariatePolynomial inherited from
SparseUnivariateSkewPolynomial) -- we just want to reuse
representation and _some_ operations.

--
Waldek Hebisch
heb...@math.uni.wroc.pl

Reply all
Reply to author
Forward
0 new messages