Changes http://wiki.axiom-developer.org/RecSpadPamphlet/diff
--
??changed:
The package defined in this file provide an operator for the
- n\textsuperscript{th} term of a recurrence and an operator for the
+ $n$\textsuperscript{th} term of a recurrence and an operator for the
coefficient of $x^n$ in a function specified by a functional equation.
++added:
+ getADE: F -> F
+ ++ \spad{getADE f} returns the defining equation, if f stands for the
+ ++ coefficient of an ADE.
+
-- should be local
??changed:
Implementation == add
-
+<<implementation: RecurrenceOperator>>
+@
+
+\subsection{Defining new operators}
+
+We define two new operators, one for recurrences, the other for functional
+equations. The operators for recurrences represents the $n$\textsuperscript{th}
+term of the corresponding sequence, the other the coefficient of $x^n$ in the
+Taylor series expansion.
+
+<<implementation: RecurrenceOperator>>=
oprecur := operator("rootOfRec"::Symbol)$BasicOperator
??changed:
setProperty(opADE, "%dummyVar", 2 pretend None)
-
--- this implies that the second and third arguments of oprecur are dummy
--- variables and affects tower$ES:
--- the second argument will not appear in tower$ES, if it does not appear in
--- any argument but the first and second.
--- the third argument will not appear in tower$ES, if it does not appear in any
--- other argument. (%defsum is a good example)
-
--- The arguments of these operators are as follows:
-
--- 1. eq, i.e. the vanishing expression
-
+@
+
+Setting these properties implies that the second and third arguments of oprecur
+are dummy variables and affects [[tower$ES]]: the second argument will not
+appear in [[tower$ES]], if it does not appear in any argument but the first and
+second. The third argument will not appear in [[tower$ES]], if it does not
appear
+in any other argument. ([[%defsum]] is a good example)
+
+The arguments of the two operators are as follows:
+
+\begin{enumerate}
+\item [[eq]], i.e. the vanishing expression
+
+<<implementation: RecurrenceOperator>>=
eqAsF: List F -> F
??changed:
eqAsF l == l.1
-
--- 2. dummy
-
+@
+
+\item [[dummy]], a dummy variable to make substitutions possible
+
+<<implementation: RecurrenceOperator>>=
dummy: List F -> Symbol
??changed:
dummyAsF l == l.2
-
--- 3. variable, i.e., for display
-
+@
+
+\item the variable for display
+
+<<implementation: RecurrenceOperator>>=
displayVariable: List F -> F
??changed:
displayVariable l == l.3
-
--- 4. operatorname(argument)
-
+@
+
+\item [[operatorName(argument)]]
+
+<<implementation: RecurrenceOperator>>=
operatorName: List F -> BasicOperator
??changed:
operatorArgument l == argument(kernels(l.4).1).1
-
--- rootOfADE: note that although we have arg as argument of the operator,
--- it is intended to indicate the coefficient, not the argument
--- of the power series
-
--- 5.- values in reversed order
--- rootOfRec:
--- maybe "values" should be preceded by the index of the first given
--- value. Currently, the last value is interpreted as f(0)
-
--- rootOfADE:
--- values are the first few coefficients of the power series expansion in order
-
+@
+
+Concerning [[rootOfADE]], note that although we have [[arg]] as argument of the
+operator, it is intended to indicate the coefficient, not the argument of the
+power series.
+
+
+\item [[values]] in reversed order.
+
+ \begin{itemize}
+ \item [[rootOfRec]]: maybe [[values]] should be preceded by the index of the
+ first given value. Currently, the last value is interpreted as $f(0)$.
+
+ \item [[rootOfADE]]: values are the first few coefficients of the power
+ series expansion in order.
+ \end{itemize}
+
+<<implementation: RecurrenceOperator>>=
initialValues: List F -> List F
??changed:
initialValues l == rest(l, 4)
-
+@
+\end{enumerate}
+
+\subsection{Recurrences}
+
+\subsubsection{Extracting some information from the recurrence}
+
+We need to find out wether we can determine the next term of the sequence, and
+how many initial values are necessary.
+
+<<implementation: RecurrenceOperator>>=
if R has Ring then
++added:
+-- if the recurrence is of the form
+-- $p(n, f(n+m-o), f(n+m-o+1), \dots, f(n+m)) = 0$
+-- in which case shiftInfoRec returns [m, o, f(n+m)].
??changed:
--- We consider only those kernels that have op as operator. If there is non, we
--- raise an error. For the moment we don't allow recursions that contain op
+-- We consider only those kernels that have op as operator. If there is none,
+-- we raise an error. For the moment we don't allow recursions that contain op
-- inside of another operator.
??changed:
[maxShift, maxShift - minShift, nextKernel]
-
--- try to evaluate:
+@
+
+\subsubsection{Evaluating a recurrence}
+
+<<implementation: RecurrenceOperator>>=
evalRec(op, argsym, argdisp, arg, eq, values) ==
num := numer p
++added:
+
+-- If the degree is 1, we can return the function explicitly.
+
if degree num = 1 then
??changed:
if degree num = 1 then
- eval(-coefficient(num, 0)/coefficient(num, 1), argsym::F, arg::F)
+ eval(-coefficient(num, 0)/coefficient(num, 1), argsym::F,
+ arg::F-(shiftInfo.max)::Integer::F)
else
??changed:
- if denom p = 1 and degree num = 1 then
+ if degree num = 1 then
??changed:
numberOfValues
-
+@
+
+\subsubsection{Setting the evaluation property of [[oprecur]]}
+
+[[irecur]] is just a wrapper that allows us to write a recurrence relation as
+an operator.
+
+<<implementation: RecurrenceOperator>>=
irecur: List F -> F
--removed:
irecur: List F -> F
--- This is just a wrapper that allows us to write a recurrence relation as an
--- operator.
irecur l ==
++added:
+@
+
+\subsubsection{Displaying a recurrence relation}
+
+<<implementation: RecurrenceOperator>>=
+ ddrec: List F -> OutputForm
+ ddrec l ==
+ op := operatorName l
+ values := reverse l
+ eq := eqAsF l
+
+ numberOfValues := numberOfValuesNeeded(#values-4, op, dummy l, eq)
+
+ vals: List OutputForm
+ := cons(eval(eq, dummyAsF l, displayVariable l)::OutputForm = _
+ 0::OutputForm,
+ [elt(op::OutputForm, [(i-1)::OutputForm]) = _
+ (values.i)::OutputForm
+ for i in 1..numberOfValues])
+
+ bracket(hconcat([(operatorNameAsF l)::OutputForm,
+ ": ",
+ commaSeparate vals]))
+
+ setProperty(oprecur, "%specialDisp",
+ ddrec@(List F -> OutputForm) pretend None)
+
+@
+
+\subsection{Functional Equations}
+
+\subsubsection{Extracting some information from the functional equation}
+
+[[getOrder]] returns the maximum derivative of [[op]] occurring in [[f]].
+
+<<implementation: RecurrenceOperator>>=
getOrder(op: BasicOperator, f: Kernel F): NonNegativeInteger ==
??changed:
--- try to evaluate:
+@
+
+\subsubsection{Extracting a coefficient given a functional equation}
+
+<<implementation: RecurrenceOperator>>=
evalADE(op, argsym, argdisp, arg, eq, values) ==
??changed:
if ((n := retractIfCan(arg)@Union(Integer, "failed")) case "failed")
- then kernel(opADE,
- append([eq, argsym::F, argdisp, op(arg)], values))
+ then
+--
+-- The following would need yet another operator, namely "coefficient of".
+--
+-- keq := kernels eq
+-- order := getOrder(op, keq.1)
+-- for k in rest keq repeat order := max(order, getOrder(op, k))
+--
+-- if zero? order then
+-- -- in this case, we have an algebraic equation
+--
+-- p: Fraction SparseUnivariatePolynomial F
+-- := univariate(eq, kernels(D(op(argsym::F), argsym, order)).1)$F
+--
+-- num := numer p
+--
+-- if one? degree num then
+-- -- the equation is in fact linear
+-- return eval(-coefficient(num, 0)/coefficient(num, 1),
argsym::F, arg::F)
+--
+ kernel(opADE,
+ append([eq, argsym::F, argdisp, op(arg)], values))
else
order := getOrder(op, keq.1)
++added:
+ output(hconcat("The order is ", order::OutputForm))$OutputPackage
for k in rest keq repeat order := max(order, getOrder(op, k))
++added:
+ output(hconcat("p: ", p::OutputForm))$OutputPackage
if degree numer p > 1
??changed:
else
- cen: F := 0$F
-
- s := seriesSolve(eq, op, argsym::F=cen, first(values, order))
- $ExpressionSpaceODESolver(R, F)
- r := retract(s)
- $AnyFunctions1(UnivariateTaylorSeries(F, argsym, cen))
-
- elt(r, n::Integer::NonNegativeInteger)
+ s := seriesSolve(eq, op, argsym, first(reverse values, order))
+ $ExpressionSolve(R, F,
+ UnivariateFormalPowerSeries F,
+ UnivariateFormalPowerSeries
+
SparseUnivariatePolynomialExpressions F)
+
+ elt(s, n::Integer::NonNegativeInteger)
??changed:
- ddrec: List F -> OutputForm
- ddrec l ==
- op := operatorName l
- values := reverse l
- eq := eqAsF l
-
- numberOfValues := numberOfValuesNeeded(#values-4, op, dummy l, eq)
-
- vals: List OutputForm
- := cons(eval(eq, dummyAsF l, displayVariable l)::OutputForm = _
- 0::OutputForm,
- [elt(op::OutputForm, [(i-1)::OutputForm]) = _
- (values.i)::OutputForm
- for i in 1..numberOfValues])
-
- bracket(hconcat([(operatorNameAsF l)::OutputForm,
- ": ",
- commaSeparate vals]))
-
-[5 more lines...]
+ getADE(f: F): F ==
+ ker := kernels f
+ if one?(#ker) and is?(operator(ker.1), "rootOfADE"::Symbol) then
+ l := argument(ker.1)
+ eval(eqAsF l, dummyAsF l, displayVariable l)
+ else
+ error "getADE: argument should be a single rootOfADE object"
+
+@
+%$
+\subsubsection{Displaying a functional equation}
+
+<<implementation: RecurrenceOperator>>=
ddADE: List F -> OutputForm
--
forwarded from http://wiki.axiom-developer.org/[EMAIL PROTECTED]